diff --git a/software/minizinc/.clang-format b/software/minizinc/.clang-format
new file mode 100644
index 0000000..b74e54c
--- /dev/null
+++ b/software/minizinc/.clang-format
@@ -0,0 +1,21 @@
+---
+BasedOnStyle: Google
+
+ColumnLimit: 100
+DerivePointerAlignment: false
+AccessModifierOffset: -2
+
+IncludeBlocks: Regroup
+IncludeCategories:
+ - Regex: '^( download.sh
+ - sh download.sh vendor master vendor:${MZNARCH} vendor.zip
+ - unzip -q vendor.zip
+
+.download_vendor_win: &download_vendor_win
+ - curl -o download.sh --location --header "PRIVATE-TOKEN:%ACCESS_TOKEN%" --silent https://gitlab.com/api/v4/snippets/1796163/raw
+ - dos2unix download.sh
+ - sh download.sh vendor master vendor:%MZNARCH% vendor.zip
+ - unzip -q vendor.zip
+
+.download_bundle: &download_bundle
+ - curl --location --header "PRIVATE-TOKEN:$ACCESS_TOKEN" --silent https://gitlab.com/api/v4/snippets/1796163/raw | tr -d '\r' > download.sh
+ - sh download.sh vendor master bundle:${MZNARCH} vendor.zip
+ - unzip -q vendor.zip
+
+.download_bundle_win: &download_bundle_win
+ - curl -o download.sh --location --header "PRIVATE-TOKEN:%ACCESS_TOKEN%" --silent https://gitlab.com/api/v4/snippets/1796163/raw
+ - dos2unix download.sh
+ - sh download.sh vendor master bundle:%MZNARCH% vendor.zip
+ - unzip -q vendor.zip
+
+variables:
+ # CCache settings
+ CCACHE_DIR: "$CI_PROJECT_DIR/.ccache"
+ CCACHE_MAXSIZE: "100M"
+
+default:
+ interruptible: true
+
+# ----------- Build MiniZinc -----------
+
+.build:
+ stage: build
+ before_script:
+ - *download_vendor
+ script:
+ - cmake -S . -B build -G"$CMAKE_ARCH" -DCMAKE_BUILD_TYPE=Release -DBUILD_REF=$CI_PIPELINE_ID -DUSE_PROPRIETARY=OFF -DGecode_ROOT="$CI_PROJECT_DIR/vendor/gecode" -DGurobi_ROOT="$CI_PROJECT_DIR/vendor/gurobi" -DCPlex_ROOT="$CI_PROJECT_DIR/vendor/CPLEX_Studio/cplex" -DOsiCBC_ROOT="$CI_PROJECT_DIR/vendor/cbc" -DSCIP_ROOT="$CI_PROJECT_DIR/vendor/scip" -DXpress_ROOT="$CI_PROJECT_DIR/vendor/xpressmp" -DCMAKE_INSTALL_PREFIX="$CI_PROJECT_DIR/minizinc"
+ - cmake --build build --config Release --target install
+ artifacts:
+ paths: [minizinc/]
+ cache:
+ key: "$CI_JOB_STAGE:$CI_JOB_NAME"
+ paths: [.ccache, vendor.zip*]
+ only: [tags, merge_requests, pipelines, develop, master, feature/on_restart]
+
+build:linux:
+ extends: .build
+ image: minizinc/build-environment:cpp
+ variables:
+ MZNARCH: "linux"
+ CMAKE_ARCH: "Ninja"
+ tags: [linux, docker]
+
+build:musl:
+ extends: .build
+ image: minizinc/build-environment:alpine
+ variables:
+ MZNARCH: "musl"
+ CMAKE_ARCH: "Ninja"
+ tags: [linux, docker]
+
+build:osx:
+ extends: .build
+ variables:
+ MZNARCH: "osx"
+ CMAKE_ARCH: "Ninja"
+ tags: [osx, cmake, cpp]
+
+build:win64:
+ extends: .build
+ variables:
+ MZNARCH: "win64"
+ CMAKE_ARCH: "Ninja"
+ BUILDCACHE_DIR: "$CI_PROJECT_DIR/.ccache"
+ BUILDCACHE_MAX_CACHE_SIZE: "104857600"
+ before_script:
+ - *download_vendor_win
+ script:
+ - cmake -S . -B build -G"%CMAKE_ARCH%" -DCMAKE_BUILD_TYPE=Release -DBUILD_REF=%CI_PIPELINE_ID% -DCCACHE_PROGRAM:STRING=buildcache -DUSE_PROPRIETARY=OFF -DGecode_ROOT="%CI_PROJECT_DIR%/vendor/gecode" -DGurobi_ROOT="%CI_PROJECT_DIR%/vendor/gurobi" -DCPlex_ROOT="%CI_PROJECT_DIR%/vendor/CPLEX_Studio/cplex" -DOsiCBC_ROOT="%CI_PROJECT_DIR%/vendor/cbc" -DSCIP_ROOT="%CI_PROJECT_DIR%/vendor/scip" -DXpress_ROOT="%CI_PROJECT_DIR%/vendor/xpressmp" -DCMAKE_INSTALL_PREFIX="%CI_PROJECT_DIR%/minizinc"
+ - cmake --build build --config Release --target install
+ cache:
+ key: "build_win64"
+ tags: [win64, cmake, cpp, ninja, buildcache]
+
+build:wasm_complete:
+ extends: .build
+ image: emscripten/emsdk
+ variables:
+ MZNARCH: "wasm"
+ CMAKE_ARCH: "Unix Makefiles"
+ script:
+ - apt-get update && apt-get install -qq python3
+ - emcmake cmake -S . -B build -G"$CMAKE_ARCH" -DCMAKE_FIND_ROOT_PATH="/" -DCMAKE_BUILD_TYPE=MinSizeRel -v -DBUILD_REF=$CI_PIPELINE_ID -DUSE_PROPRIETARY=OFF -DGecode_ROOT="$CI_PROJECT_DIR/vendor/gecode" -DGurobi_ROOT="$CI_PROJECT_DIR/vendor/gurobi" -DCPlex_ROOT="$CI_PROJECT_DIR/vendor/CPLEX_Studio/cplex" -DOsiCBC_ROOT="$CI_PROJECT_DIR/vendor/cbc" -DSCIP_ROOT="$CI_PROJECT_DIR/vendor/scip" -DXpress_ROOT="$CI_PROJECT_DIR/vendor/xpressmp" -DCMAKE_INSTALL_PREFIX="$CI_PROJECT_DIR/minizinc"
+ - cmake --build build --config MinSizeRel --target install
+ tags: [docker, high-mem]
+ when: manual
+
+build:wasm_minimal:
+ extends: .build
+ image: emscripten/emsdk
+ variables:
+ MZNARCH: "wasm"
+ CMAKE_ARCH: "Unix Makefiles"
+ script:
+ - apt-get update && apt-get install -qq python3
+ - emcmake cmake -S . -B build -G"$CMAKE_ARCH" -DCMAKE_BUILD_TYPE=MinSizeRel -v -DBUILD_REF=$CI_PIPELINE_ID -DUSE_PROPRIETARY=OFF -DGecode_ROOT="$CI_PROJECT_DIR/vendor/gecode" -DGurobi_ROOT="$CI_PROJECT_DIR/vendor/gurobi" -DCPlex_ROOT="$CI_PROJECT_DIR/vendor/CPLEX_Studio/cplex" -DOsiCBC_ROOT="$CI_PROJECT_DIR/vendor/cbc" -DSCIP_ROOT="$CI_PROJECT_DIR/vendor/scip" -DXpress_ROOT="$CI_PROJECT_DIR/vendor/xpressmp" -DCMAKE_INSTALL_PREFIX="$CI_PROJECT_DIR/minizinc"
+ - cmake --build build --config MinSizeRel --target install
+ tags: [docker]
+ when: manual
+
+# ----------- Test Suite -----------
+
+test:format:
+ stage: test
+ image: minizinc/build-environment:clang-format
+ script:
+ - cmake -S . -B build -GNinja -DCLANG_FORMAT_EXECUTABLE="run-clang-format" -DCLANG_FORMAT_FLAGS="--color always"
+ - cmake --build build --target format
+ tags: [linux, docker]
+ only:
+ changes:
+ - "**/*.{cpp,c,h,hh,hpp}"
+ - .clang-format
+ refs:
+ - merge_requests
+ needs: []
+
+test:analyse:
+ extends: .build
+ stage: test
+ image: minizinc/build-environment:clang-tidy
+ variables:
+ MZNARCH: "linux"
+ CMAKE_ARCH: "Ninja"
+ script:
+ - cmake -S . -B build -G"$CMAKE_ARCH" -DCMAKE_CXX_CLANG_TIDY="clang-tidy" -DCMAKE_BUILD_TYPE="Debug" -DGecode_ROOT="$CI_PROJECT_DIR/vendor/gecode" -DGurobi_ROOT="$CI_PROJECT_DIR/vendor/gurobi" -DCPlex_ROOT="$CI_PROJECT_DIR/vendor/CPLEX_Studio/cplex" -DOsiCBC_ROOT="$CI_PROJECT_DIR/vendor/cbc" -DSCIP_ROOT="$CI_PROJECT_DIR/vendor/scip" -DXpress_ROOT="$CI_PROJECT_DIR/vendor/xpressmp"
+ - cmake --build build --config Debug
+ tags: [linux, docker]
+ only:
+ changes:
+ - "**/*.{cpp,c,h,hh,hpp}"
+ - .clang-tidy
+ refs:
+ - merge_requests
+ needs: []
+
+.tests:
+ stage: test
+ variables:
+ PIP_CACHE_DIR: "$CI_PROJECT_DIR/.cache/pip"
+ MZN_SOLVER_PATH: "$CI_PROJECT_DIR/vendor/chuffed/share/minizinc/solvers/:$CI_PROJECT_DIR/vendor/gecode"
+ before_script:
+ - *download_bundle
+ # TODO: Add gecode configuration to the Gecode solver
+ - 'echo ''{"id":"org.gecode.gecode","name":"Gecode","description":"Gecode FlatZinc executable","version":"6.1.1","mznlib":"share/gecode/mznlib","executable":"bin/fzn-gecode","tags":["cp","int","float","set","restart"],"stdFlags":["-a","-f","-n","-p","-r","-s","-t"],"extraFlags":[["-c-d","Recomputation commit distance","int","8"],["-a-d","Recomputation adaption distance","int","2"],["-decay","Decay factor","float","0.99"],["-node","Node cutoff","int","0"],["-fail","Failure cutoff","int","0"],["-restart","Restart sequence type","opt:none:constant:linear:luby:geometric","none"],["-restart-base","Base for geometric restart sequence","float","1.5"],["-restart-scale","Scale factor for restart sequence","int","250"],["-nogoods","Use no-goods from restarts","bool","false"],["-nogoods-limit","Depth limit for no-good extraction","int","128"]],"supportsMzn":false,"supportsFzn":true,"needsSolns2Out":true,"needsMznExecutable":false,"needsStdlibDir":false,"isGUIApplication":false}'' > vendor/gecode/gecode.msc'
+ - export PATH=$CI_PROJECT_DIR/minizinc/bin:$PATH
+ - minizinc --solvers
+ - cd tests
+ - python3 -m venv env
+ - source env/bin/activate
+ - pip install -r requirements.txt
+ after_script:
+ - echo "Test results at https://minizinc.gitlab.io/-/minizinc/-/jobs/${CI_JOB_ID}/artifacts/tests/output/report.html"
+ artifacts:
+ when: always
+ paths:
+ - tests/output
+ reports:
+ junit: tests/output/junit*.xml
+ cache:
+ key: "$CI_JOB_STAGE:$CI_JOB_NAME"
+ paths: [.cache/pip, vendor.zip*]
+ only: [merge_requests, pipelines, master]
+
+# Linux specific config
+.tests_linux:
+ extends: .tests
+ image: python:latest
+ variables:
+ MZNARCH: "linux"
+ tags: [linux, docker]
+ dependencies: ["build:linux"]
+ needs: ["build:linux"]
+
+# OSX specific config
+.tests_osx:
+ extends: .tests
+ variables:
+ MZNARCH: "osx"
+ tags: [osx]
+ dependencies: ["build:osx"]
+ needs: ["build:osx"]
+
+# Windows specific config
+.tests_win64:
+ extends: .tests
+ variables:
+ MZNARCH: "win64"
+ MZN_SOLVER_PATH: "$CI_PROJECT_DIR/vendor/chuffed/share/minizinc/solvers;$CI_PROJECT_DIR/vendor/gecode"
+ before_script:
+ - *download_bundle_win
+ # TODO: Add gecode configuration to the Gecode solver
+ - 'echo {"id":"org.gecode.gecode","name":"Gecode","description":"Gecode FlatZinc executable","version":"6.1.1","mznlib":"share/gecode/mznlib","executable":"bin/fzn-gecode","tags":["cp","int","float","set","restart"],"stdFlags":["-a","-f","-n","-p","-r","-s","-t"],"extraFlags":[["-c-d","Recomputation commit distance","int","8"],["-a-d","Recomputation adaption distance","int","2"],["-decay","Decay factor","float","0.99"],["-node","Node cutoff","int","0"],["-fail","Failure cutoff","int","0"],["-restart","Restart sequence type","opt:none:constant:linear:luby:geometric","none"],["-restart-base","Base for geometric restart sequence","float","1.5"],["-restart-scale","Scale factor for restart sequence","int","250"],["-nogoods","Use no-goods from restarts","bool","false"],["-nogoods-limit","Depth limit for no-good extraction","int","128"]],"supportsMzn":false,"supportsFzn":true,"needsSolns2Out":true,"needsMznExecutable":false,"needsStdlibDir":false,"isGUIApplication":false} > vendor/gecode/gecode.msc'
+ - set PATH=%CI_PROJECT_DIR%/minizinc/bin;%PATH%
+ - cd tests
+ - python -m venv env
+ - call env\Scripts\activate.bat
+ - pip install -r requirements.txt
+ after_script:
+ - "echo Test results at https://minizinc.gitlab.io/-/minizinc/-/jobs/%CI_JOB_ID%/artifacts/tests/output/report.html"
+ tags: [win64]
+ dependencies: ["build:win64"]
+ needs: ["build:win64"]
+ cache:
+ key: test_win64
+
+.tests_fast:
+ script:
+ - pytest
+
+.tests_full:
+ script:
+ - pytest --all-suites
+ when: manual
+
+test:linux:fast:
+ extends: [.tests_linux, .tests_fast]
+
+test:linux:full:
+ extends: [.tests_linux, .tests_full]
+
+test:osx:fast:
+ extends: [.tests_osx, .tests_fast]
+
+test:osx:full:
+ extends: [.tests_osx, .tests_full]
+
+test:win64:fast:
+ extends: [.tests_win64, .tests_fast]
+ cache:
+ key: test_win64_fast
+
+test:win64:full:
+ extends: [.tests_win64, .tests_full]
+ cache:
+ key: test_win64_full
+
+# ----------- Documentation -----------
+
+documentation:
+ stage: test
+ image: guidotack/sphinx-doc:latest
+ variables:
+ MZNARCH: "linux"
+ before_script:
+ - *download_bundle
+ script:
+ - cp $CI_PROJECT_DIR/share/minizinc/gecode_presolver/gecode.mzn $CI_PROJECT_DIR/share/minizinc/std/
+ - cp $CI_PROJECT_DIR/vendor/chuffed/share/minizinc/chuffed/chuffed.mzn $CI_PROJECT_DIR/share/minizinc/std/
+ - echo 'include "globals.mzn"; include "gecode.mzn"; include "chuffed.mzn";' > $CI_PROJECT_DIR/share/minizinc/std/all.mzn
+ - ./minizinc/bin/mzn2doc --rst-output --include-stdlib --output-base $CI_PROJECT_DIR/docs/en/lib $CI_PROJECT_DIR/share/minizinc/std/all.mzn
+ - ./minizinc/bin/mzn2doc --rst-output --include-stdlib --output-base $CI_PROJECT_DIR/docs/chi/lib $CI_PROJECT_DIR/share/minizinc/std/all.mzn
+ - cd $CI_PROJECT_DIR/docs/en
+ - make html latexpdf
+ - cd $CI_PROJECT_DIR/docs/chi
+ - make html latexpdf
+ - mkdir -p $CI_PROJECT_DIR/docs-deploy/en
+ - mkdir -p $CI_PROJECT_DIR/docs-deploy/chi
+ - cp -r $CI_PROJECT_DIR/docs/en/_build/html/* $CI_PROJECT_DIR/docs-deploy/en/
+ - cp $CI_PROJECT_DIR/docs/en/_build/latex/MiniZinc.pdf $CI_PROJECT_DIR/docs-deploy/en/MiniZinc\ Handbook.pdf
+ - cp -r $CI_PROJECT_DIR/docs/chi/_build/html/* $CI_PROJECT_DIR/docs-deploy/chi/
+ - cp $CI_PROJECT_DIR/docs/chi/_build/latex/MiniZinc.pdf $CI_PROJECT_DIR/docs-deploy/chi/MiniZinc\ Handbook.pdf
+ artifacts:
+ paths:
+ - docs-deploy
+ tags:
+ - linux
+ - docker
+ only: [tags, merge_requests, pipelines, develop, master]
+ dependencies: ["build:linux"]
+ needs: ["build:linux"]
+
+# ----------- Trigger FindMUS pipeline -----------
+
+trigger:findmus:
+ stage: trigger
+ trigger:
+ project: minizinc/FindMUS
+ branch: develop
+ only: [develop]
diff --git a/software/minizinc/CMakeLists.txt b/software/minizinc/CMakeLists.txt
new file mode 100644
index 0000000..ceb5890
--- /dev/null
+++ b/software/minizinc/CMakeLists.txt
@@ -0,0 +1,108 @@
+cmake_minimum_required(VERSION 3.4.0)
+set(CMAKE_OSX_DEPLOYMENT_TARGET "10.9" CACHE STRING "Minimum OS X deployment version") # Must be before project()
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- Project information and versioning.
+
+project(libminizinc
+ VERSION 2.5.5
+ LANGUAGES CXX C)
+
+if(NOT BUILD_REF)
+ set(BUILD_REF "")
+endif()
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- Project build options
+
+# Static vs. Dynamic linking
+option(CPlex_PLUGIN "Build CPLEX binding as a plugin" ON)
+option(Gurobi_PLUGIN "Build Gurobi binding as a plugin" ON)
+
+# Enforce non proprietary build
+option(USE_PROPRIETARY "Enable static linking of proprietary solvers" OFF)
+if(NOT USE_PROPRIETARY)
+ set(CPLEX_PLUGIN ON)
+ set(GUROBI_PLUGIN ON)
+endif()
+
+# CMake options default value
+option(CMAKE_POSITION_INDEPENDENT_CODE "Default value for POSITION_INDEPENDENT_CODE of targets" TRUE)
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- CMake initialisation
+
+include(GNUInstallDirs)
+
+# Fix library suffixes for Web Assembly platform
+include(cmake/support/emscripten_setup.cmake)
+
+# Try to find possible dependencies
+list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/cmake/modules)
+if(POLICY CMP0074)
+ cmake_policy(SET CMP0074 NEW)
+endif(POLICY CMP0074)
+find_package(CPlex)
+find_package(Geas)
+find_package(Gecode 6.0 COMPONENTS Driver Float Int Kernel Minimodel Search Set Support)
+find_package(Gurobi)
+find_package(OsiCBC)
+find_package(SCIP)
+find_package(Xpress)
+
+# Set build type when none is selected
+set(DEFAULT_BUILD_TYPE "Release")
+if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
+ message(STATUS "Setting build type to '${DEFAULT_BUILD_TYPE}' as none was specified.")
+ set(CMAKE_BUILD_TYPE "${DEFAULT_BUILD_TYPE}" CACHE STRING "Choose the type of build." FORCE)
+ # Set the possible values of build type for cmake-gui
+ set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS
+ "Debug"
+ "Release"
+ "MinSizeRel"
+ "RelWithDebInfo")
+endif()
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- Compiler configuration
+
+include(cmake/support/ccache_setup.cmake)
+include(cmake/support/compiler_setup.cmake)
+
+configure_file(
+ ${PROJECT_SOURCE_DIR}/include/minizinc/config.hh.in
+ ${PROJECT_BINARY_DIR}/include/minizinc/config.hh
+)
+
+install(
+ FILES ${PROJECT_BINARY_DIR}/include/minizinc/config.hh
+ DESTINATION include/minizinc
+)
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- MiniZinc compilation targets.
+
+find_package(Threads REQUIRED)
+include_directories(${PROJECT_SOURCE_DIR}/include)
+include_directories(${PROJECT_BINARY_DIR}/include)
+
+# Libraries
+include(cmake/targets/libmzn.cmake)
+
+# Executables
+include(cmake/targets/minizinc.cmake)
+include(cmake/targets/mzn2doc.cmake)
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- Platform Specific configuration
+include(cmake/support/config_emscripten.cmake)
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- CMake configuration generation
+
+include(cmake/support/config_export.cmake)
+include(cmake/support/config_output.cmake)
+
+# -------------------------------------------------------------------------------------------------------------------
+# -- Support Actions
+include(cmake/support/format.cmake)
diff --git a/software/minizinc/LICENSE.txt b/software/minizinc/LICENSE.txt
new file mode 100644
index 0000000..dec4bbc
--- /dev/null
+++ b/software/minizinc/LICENSE.txt
@@ -0,0 +1,377 @@
+If not noted otherwise in individual file headers, all files that make up
+the libminizinc distribution are released under the Mozilla Public License
+Version 2.0, a copy of which can be found below.
+
+Mozilla Public License Version 2.0
+==================================
+
+1. Definitions
+--------------
+
+1.1. "Contributor"
+ means each individual or legal entity that creates, contributes to
+ the creation of, or owns Covered Software.
+
+1.2. "Contributor Version"
+ means the combination of the Contributions of others (if any) used
+ by a Contributor and that particular Contributor's Contribution.
+
+1.3. "Contribution"
+ means Covered Software of a particular Contributor.
+
+1.4. "Covered Software"
+ means Source Code Form to which the initial Contributor has attached
+ the notice in Exhibit A, the Executable Form of such Source Code
+ Form, and Modifications of such Source Code Form, in each case
+ including portions thereof.
+
+1.5. "Incompatible With Secondary Licenses"
+ means
+
+ (a) that the initial Contributor has attached the notice described
+ in Exhibit B to the Covered Software; or
+
+ (b) that the Covered Software was made available under the terms of
+ version 1.1 or earlier of the License, but not also under the
+ terms of a Secondary License.
+
+1.6. "Executable Form"
+ means any form of the work other than Source Code Form.
+
+1.7. "Larger Work"
+ means a work that combines Covered Software with other material, in
+ a separate file or files, that is not Covered Software.
+
+1.8. "License"
+ means this document.
+
+1.9. "Licensable"
+ means having the right to grant, to the maximum extent possible,
+ whether at the time of the initial grant or subsequently, any and
+ all of the rights conveyed by this License.
+
+1.10. "Modifications"
+ means any of the following:
+
+ (a) any file in Source Code Form that results from an addition to,
+ deletion from, or modification of the contents of Covered
+ Software; or
+
+ (b) any new file in Source Code Form that contains any Covered
+ Software.
+
+1.11. "Patent Claims" of a Contributor
+ means any patent claim(s), including without limitation, method,
+ process, and apparatus claims, in any patent Licensable by such
+ Contributor that would be infringed, but for the grant of the
+ License, by the making, using, selling, offering for sale, having
+ made, import, or transfer of either its Contributions or its
+ Contributor Version.
+
+1.12. "Secondary License"
+ means either the GNU General Public License, Version 2.0, the GNU
+ Lesser General Public License, Version 2.1, the GNU Affero General
+ Public License, Version 3.0, or any later versions of those
+ licenses.
+
+1.13. "Source Code Form"
+ means the form of the work preferred for making modifications.
+
+1.14. "You" (or "Your")
+ means an individual or a legal entity exercising rights under this
+ License. For legal entities, "You" includes any entity that
+ controls, is controlled by, or is under common control with You. For
+ purposes of this definition, "control" means (a) the power, direct
+ or indirect, to cause the direction or management of such entity,
+ whether by contract or otherwise, or (b) ownership of more than
+ fifty percent (50%) of the outstanding shares or beneficial
+ ownership of such entity.
+
+2. License Grants and Conditions
+--------------------------------
+
+2.1. Grants
+
+Each Contributor hereby grants You a world-wide, royalty-free,
+non-exclusive license:
+
+(a) under intellectual property rights (other than patent or trademark)
+ Licensable by such Contributor to use, reproduce, make available,
+ modify, display, perform, distribute, and otherwise exploit its
+ Contributions, either on an unmodified basis, with Modifications, or
+ as part of a Larger Work; and
+
+(b) under Patent Claims of such Contributor to make, use, sell, offer
+ for sale, have made, import, and otherwise transfer either its
+ Contributions or its Contributor Version.
+
+2.2. Effective Date
+
+The licenses granted in Section 2.1 with respect to any Contribution
+become effective for each Contribution on the date the Contributor first
+distributes such Contribution.
+
+2.3. Limitations on Grant Scope
+
+The licenses granted in this Section 2 are the only rights granted under
+this License. No additional rights or licenses will be implied from the
+distribution or licensing of Covered Software under this License.
+Notwithstanding Section 2.1(b) above, no patent license is granted by a
+Contributor:
+
+(a) for any code that a Contributor has removed from Covered Software;
+ or
+
+(b) for infringements caused by: (i) Your and any other third party's
+ modifications of Covered Software, or (ii) the combination of its
+ Contributions with other software (except as part of its Contributor
+ Version); or
+
+(c) under Patent Claims infringed by Covered Software in the absence of
+ its Contributions.
+
+This License does not grant any rights in the trademarks, service marks,
+or logos of any Contributor (except as may be necessary to comply with
+the notice requirements in Section 3.4).
+
+2.4. Subsequent Licenses
+
+No Contributor makes additional grants as a result of Your choice to
+distribute the Covered Software under a subsequent version of this
+License (see Section 10.2) or under the terms of a Secondary License (if
+permitted under the terms of Section 3.3).
+
+2.5. Representation
+
+Each Contributor represents that the Contributor believes its
+Contributions are its original creation(s) or it has sufficient rights
+to grant the rights to its Contributions conveyed by this License.
+
+2.6. Fair Use
+
+This License is not intended to limit any rights You have under
+applicable copyright doctrines of fair use, fair dealing, or other
+equivalents.
+
+2.7. Conditions
+
+Sections 3.1, 3.2, 3.3, and 3.4 are conditions of the licenses granted
+in Section 2.1.
+
+3. Responsibilities
+-------------------
+
+3.1. Distribution of Source Form
+
+All distribution of Covered Software in Source Code Form, including any
+Modifications that You create or to which You contribute, must be under
+the terms of this License. You must inform recipients that the Source
+Code Form of the Covered Software is governed by the terms of this
+License, and how they can obtain a copy of this License. You may not
+attempt to alter or restrict the recipients' rights in the Source Code
+Form.
+
+3.2. Distribution of Executable Form
+
+If You distribute Covered Software in Executable Form then:
+
+(a) such Covered Software must also be made available in Source Code
+ Form, as described in Section 3.1, and You must inform recipients of
+ the Executable Form how they can obtain a copy of such Source Code
+ Form by reasonable means in a timely manner, at a charge no more
+ than the cost of distribution to the recipient; and
+
+(b) You may distribute such Executable Form under the terms of this
+ License, or sublicense it under different terms, provided that the
+ license for the Executable Form does not attempt to limit or alter
+ the recipients' rights in the Source Code Form under this License.
+
+3.3. Distribution of a Larger Work
+
+You may create and distribute a Larger Work under terms of Your choice,
+provided that You also comply with the requirements of this License for
+the Covered Software. If the Larger Work is a combination of Covered
+Software with a work governed by one or more Secondary Licenses, and the
+Covered Software is not Incompatible With Secondary Licenses, this
+License permits You to additionally distribute such Covered Software
+under the terms of such Secondary License(s), so that the recipient of
+the Larger Work may, at their option, further distribute the Covered
+Software under the terms of either this License or such Secondary
+License(s).
+
+3.4. Notices
+
+You may not remove or alter the substance of any license notices
+(including copyright notices, patent notices, disclaimers of warranty,
+or limitations of liability) contained within the Source Code Form of
+the Covered Software, except that You may alter any license notices to
+the extent required to remedy known factual inaccuracies.
+
+3.5. Application of Additional Terms
+
+You may choose to offer, and to charge a fee for, warranty, support,
+indemnity or liability obligations to one or more recipients of Covered
+Software. However, You may do so only on Your own behalf, and not on
+behalf of any Contributor. You must make it absolutely clear that any
+such warranty, support, indemnity, or liability obligation is offered by
+You alone, and You hereby agree to indemnify every Contributor for any
+liability incurred by such Contributor as a result of warranty, support,
+indemnity or liability terms You offer. You may include additional
+disclaimers of warranty and limitations of liability specific to any
+jurisdiction.
+
+4. Inability to Comply Due to Statute or Regulation
+---------------------------------------------------
+
+If it is impossible for You to comply with any of the terms of this
+License with respect to some or all of the Covered Software due to
+statute, judicial order, or regulation then You must: (a) comply with
+the terms of this License to the maximum extent possible; and (b)
+describe the limitations and the code they affect. Such description must
+be placed in a text file included with all distributions of the Covered
+Software under this License. Except to the extent prohibited by statute
+or regulation, such description must be sufficiently detailed for a
+recipient of ordinary skill to be able to understand it.
+
+5. Termination
+--------------
+
+5.1. The rights granted under this License will terminate automatically
+if You fail to comply with any of its terms. However, if You become
+compliant, then the rights granted under this License from a particular
+Contributor are reinstated (a) provisionally, unless and until such
+Contributor explicitly and finally terminates Your grants, and (b) on an
+ongoing basis, if such Contributor fails to notify You of the
+non-compliance by some reasonable means prior to 60 days after You have
+come back into compliance. Moreover, Your grants from a particular
+Contributor are reinstated on an ongoing basis if such Contributor
+notifies You of the non-compliance by some reasonable means, this is the
+first time You have received notice of non-compliance with this License
+from such Contributor, and You become compliant prior to 30 days after
+Your receipt of the notice.
+
+5.2. If You initiate litigation against any entity by asserting a patent
+infringement claim (excluding declaratory judgment actions,
+counter-claims, and cross-claims) alleging that a Contributor Version
+directly or indirectly infringes any patent, then the rights granted to
+You by any and all Contributors for the Covered Software under Section
+2.1 of this License shall terminate.
+
+5.3. In the event of termination under Sections 5.1 or 5.2 above, all
+end user license agreements (excluding distributors and resellers) which
+have been validly granted by You or Your distributors under this License
+prior to termination shall survive termination.
+
+************************************************************************
+* *
+* 6. Disclaimer of Warranty *
+* ------------------------- *
+* *
+* Covered Software is provided under this License on an "as is" *
+* basis, without warranty of any kind, either expressed, implied, or *
+* statutory, including, without limitation, warranties that the *
+* Covered Software is free of defects, merchantable, fit for a *
+* particular purpose or non-infringing. The entire risk as to the *
+* quality and performance of the Covered Software is with You. *
+* Should any Covered Software prove defective in any respect, You *
+* (not any Contributor) assume the cost of any necessary servicing, *
+* repair, or correction. This disclaimer of warranty constitutes an *
+* essential part of this License. No use of any Covered Software is *
+* authorized under this License except under this disclaimer. *
+* *
+************************************************************************
+
+************************************************************************
+* *
+* 7. Limitation of Liability *
+* -------------------------- *
+* *
+* Under no circumstances and under no legal theory, whether tort *
+* (including negligence), contract, or otherwise, shall any *
+* Contributor, or anyone who distributes Covered Software as *
+* permitted above, be liable to You for any direct, indirect, *
+* special, incidental, or consequential damages of any character *
+* including, without limitation, damages for lost profits, loss of *
+* goodwill, work stoppage, computer failure or malfunction, or any *
+* and all other commercial damages or losses, even if such party *
+* shall have been informed of the possibility of such damages. This *
+* limitation of liability shall not apply to liability for death or *
+* personal injury resulting from such party's negligence to the *
+* extent applicable law prohibits such limitation. Some *
+* jurisdictions do not allow the exclusion or limitation of *
+* incidental or consequential damages, so this exclusion and *
+* limitation may not apply to You. *
+* *
+************************************************************************
+
+8. Litigation
+-------------
+
+Any litigation relating to this License may be brought only in the
+courts of a jurisdiction where the defendant maintains its principal
+place of business and such litigation shall be governed by laws of that
+jurisdiction, without reference to its conflict-of-law provisions.
+Nothing in this Section shall prevent a party's ability to bring
+cross-claims or counter-claims.
+
+9. Miscellaneous
+----------------
+
+This License represents the complete agreement concerning the subject
+matter hereof. If any provision of this License is held to be
+unenforceable, such provision shall be reformed only to the extent
+necessary to make it enforceable. Any law or regulation which provides
+that the language of a contract shall be construed against the drafter
+shall not be used to construe this License against a Contributor.
+
+10. Versions of the License
+---------------------------
+
+10.1. New Versions
+
+Mozilla Foundation is the license steward. Except as provided in Section
+10.3, no one other than the license steward has the right to modify or
+publish new versions of this License. Each version will be given a
+distinguishing version number.
+
+10.2. Effect of New Versions
+
+You may distribute the Covered Software under the terms of the version
+of the License under which You originally received the Covered Software,
+or under the terms of any subsequent version published by the license
+steward.
+
+10.3. Modified Versions
+
+If you create software not governed by this License, and you want to
+create a new license for such software, you may create and use a
+modified version of this License if you rename the license and remove
+any references to the name of the license steward (except to note that
+such modified license differs from this License).
+
+10.4. Distributing Source Code Form that is Incompatible With Secondary
+Licenses
+
+If You choose to distribute Source Code Form that is Incompatible With
+Secondary Licenses under the terms of this version of the License, the
+notice described in Exhibit B of this License must be attached.
+
+Exhibit A - Source Code Form License Notice
+-------------------------------------------
+
+ This Source Code Form is subject to the terms of the Mozilla Public
+ License, v. 2.0. If a copy of the MPL was not distributed with this
+ file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+If it is not possible or desirable to put the notice in a particular
+file, then You may include the notice in a location (such as a LICENSE
+file in a relevant directory) where a recipient would be likely to look
+for such a notice.
+
+You may add additional accurate notices of copyright ownership.
+
+Exhibit B - "Incompatible With Secondary Licenses" Notice
+---------------------------------------------------------
+
+ This Source Code Form is "Incompatible With Secondary Licenses", as
+ defined by the Mozilla Public License, v. 2.0.
diff --git a/software/minizinc/README.md b/software/minizinc/README.md
new file mode 100644
index 0000000..4dbf6c3
--- /dev/null
+++ b/software/minizinc/README.md
@@ -0,0 +1,168 @@
+
+
+
+
+
+
+## Table of Contents
+
+* [About the Project](#about-the-project)
+* [Getting Started](#getting-started)
+ * [Installation](#installation)
+ * [Usage](#usage)
+* [Building](#building)
+ * [Prerequisites](#prerequisites)
+ * [Compilation](#compilation)
+* [Testing](#testing)
+* [License](#license)
+* [Contact](#contact)
+
+
+
+## About The Project
+
+MiniZinc is a free and open-source constraint modeling language.
+
+You can use MiniZinc to model constraint satisfaction and optimisation problems
+in a high-level, solver-independent way, taking advantage of a large library of
+pre-defined constraints. Your model is then compiled into FlatZinc, a solver
+input language that is understood by a wide range of solvers.
+
+MiniZinc is developed at Monash University in collaboration with Data61
+Decision Sciences.
+
+
+## Getting Started
+
+To get a MiniZinc up and running follow these simple steps.
+
+### Installation
+
+The recommended way to install _MiniZinc_ is by the use of the bundled binary
+packages. These packages are available for machines running Linux, Mac, and
+Windows.
+
+The latest release can be found on [the MiniZinc
+website](http://www.minizinc.org/software.html).
+
+### Usage
+
+Once the MiniZinc bundle is installed on your machine, you can start expressing
+and solving discrete optimisation problems. The following code segment shows a
+MiniZinc model for the well known n-queens problem.
+
+```minizinc
+int: n = 8; % The number of queens.
+
+array [1..n] of var 1..n: q;
+
+include "alldifferent.mzn";
+
+constraint alldifferent(q);
+constraint alldifferent(i in 1..n)(q[i] + i);
+constraint alldifferent(i in 1..n)(q[i] - i);
+```
+
+You have two easy options to solve this model:
+ - In the MiniZincIDE: Select your preferred solver and press the "Run" button.
+ - With the `minizinc` executable available on your path: run `minizinc --solver gecode nqueens.mzn`.
+
+_For more example MiniZinc models and more information about working with
+MiniZinc, please refer to our
+[Documentation](https://www.minizinc.org/doc-latest/)_
+
+
+## Building
+
+The following instructions will help you compile the MiniZinc compiler. Note
+that this repository does not include the IDE, findMUS, or any solvers that are
+part of the MiniZinc project. These can be found in the following repositories:
+
+ - [MiniZincIDE](https://github.com/MiniZinc/MiniZincIDE)
+ - [Gecode](https://github.com/Gecode/gecode)
+ - [Chuffed](https://github.com/chuffed/chuffed)
+
+### Prerequisites
+
+- [CMake](https://cmake.org/) (>=3.4)
+- A recent C++ compiler - Compilation is tested with recent versions of Clang,
+ GCC, and Microsoft Visual C++.
+- (optional) [Bison](https://www.gnu.org/software/bison/) (>=3.4) and
+ [Flex](https://github.com/westes/flex) (>=2.5) - To make changes to the
+ MiniZinc lexer or parser.
+- (optional) [Gecode](https://www.gecode.org/) - To compile the internal Gecode
+ solver interface (included in the MiniZinc bundle)
+- (optional) [Coin OR's CBC](https://www.coin-or.org/) - To compile the
+ internal CBC solver interface (included in the MiniZinc bundle)
+- (optional) Proprietary solver headers
+ ([CPLEX](https://www.ibm.com/analytics/cplex-optimizer),
+ [Gurobi](https://www.gurobi.com/), [SCIP](https://www.scipopt.org/),
+ [Xpress](https://www.fico.com/)) - To load these solvers at runtime (included
+ in the MiniZinc bundle)
+
+### Compilation
+
+The MiniZinc compiler is compiled as a CMake project. CMake's [User Interaction
+Guide](https://cmake.org/cmake/help/latest/guide/user-interaction/index.html)
+can provide you with a quick introduction to compiling CMake projects. The
+following CMake variables can be used in the MiniZinc project to instruct the
+compilation behaviour:
+
+| Variable | Default | Description |
+|----------------------------------------------|---------|-------------------------------------------------------------|
+| CMAKE_BUILD_TYPE | Release | Build type of single-configuration generators. |
+| CMAKE_INSTALL_PREFIX | | Install directory used by `--target install`. |
+| CMAKE_POSITION_INDEPENDENT_CODE | TRUE | Whether to create a position-independent targets |
+| ****_ROOT | | Additional directory to look for **** |
+| CMAKE_DISABLE_FIND_PACKAGE_**** | FALSE | Disable compilation of ****'s solver interface |
+| USE_PROPRIETARY | FALSE | Allow static linking of proprietary solvers |
+| ****_PLUGIN | TRUE | Load solver at runtime (instead of static compilation) |
+
+Possible values for **** are `CPlex`, `Geas`, `Gecode`, `Gurobi`,
+`OsiCBC`, `SCIP`, and `Xpress`.
+
+
+## Testing
+
+The correctness of the MiniZinc compiler is tested using a
+[PyTest](https://docs.pytest.org/en/stable/) test suite. Instruction on how to
+run the test suite and how to add new tests can be found
+[here](https://github.com/MiniZinc/libminizinc/tree/master/tests)
+
+
+
+## License
+
+Distributed under the Mozilla Public License Version 2.0. See `LICENSE` for more information.
+
+
+
+## Contact
+
+🏛 **MiniZinc Community**
+ - Website: [https://www.minizinc.org/](https://www.minizinc.org/)
+ - StackOverflow: [https://stackoverflow.com/questions/tagged/minizinc](https://stackoverflow.com/questions/tagged/minizinc)
+ - Google Groups: [https://groups.google.com/g/minizinc](https://groups.google.com/g/minizinc)
+
+🏛 **Monash Optimisation Group**
+ - Website: [https://www.monash.edu/it/dsai/optimisation](https://www.monash.edu/it/dsai/optimisation)
diff --git a/software/minizinc/changes.rst b/software/minizinc/changes.rst
new file mode 100644
index 0000000..416e7a9
--- /dev/null
+++ b/software/minizinc/changes.rst
@@ -0,0 +1,2259 @@
+MiniZinc Change Log
+-------------------
+
+For detailed bug reports consult the issue tracker at
+https://github.com/MiniZinc/libminizinc/issues.
+
+.. _v2.5.5:
+
+`Version 2.5.5 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 19 March 2021)
+
+Changes:
+^^^^^^^^
+
+- Make min/max on an array of optional variables return a non-optional var,
+ behaving as if absent values are not in the array.
+
+Bug fixes:
+^^^^^^^^^^
+
+- Insert par array literals in the common subexpression elimination map, fixing
+ a FlatZinc code bloat issue (:bugref:`458`).
+
+Changes in the IDE:
+^^^^^^^^^^^^^^^^^^^
+
+- Fix editing of custom string parameters so they don't get converted to
+ floats.
+- Fix crash on Windows caused when the ``PATH`` environment contains unicode
+ characters.
+
+.. _v2.5.4:
+
+`Version 2.5.4 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 16 March 2021)
+
+Changes:
+^^^^^^^^
+
+- Allow empty arrays in global cardinality constraints (:bugref:`440`).
+- Add piecewise_linear for non-continuous intervals.
+- Fail on empty variable domains in agenda.
+- Allow coercion of JSON lists to enum definitions (:bugref:`441`).
+- Update strictly_decreasing with documentation and opt version (:bugref:`454`).
+- Remove MIP-specific ``fzn_less(eq)_bool(_reif).mzn``.
+- Add ``mzn_in_symmetry_breaking_constraint()`` for internal use.
+- Add MIP decompositions for ``lex_less[eq]_*``.
+- Add ``lex_chain_*`` globals, and use them in ``lex2[_strict]``.
+- Improve detection of variable declarations which are actually par to allow
+ more use of overloaded par versions of predicates.
+- Update documentation on installation of OR-Tools.
+- Report CPU time in ``solveTime`` statistic for MIP solvers.
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix handling of bad Xpress licenses when collecting extra flags.
+- Don't propagate annotations into annotation calls to infinite recursion.
+- Add missing par opt versions of coercion functions.
+- Revert incorrect renaming of ``has_output_item`` to ``has_outputItem`` in
+ model interface output.
+- Fix incorrect grammar specification in documentation (:bugref:`453`).
+- Fix crash when defining enums with no members (:bugref:`443`, :bugref:`444`).
+- Support undefined enums in the type checker.
+- Fix CPLEX solver ID in documentation.
+- Never insert par expressions in the common subexpression elimination map.
+- Fix cv flag propagation when the body of a let or function is cv.
+- Fix equality test for annotations involving indirection.
+- Don't modify the infinite domain of optional variables (:bugref:`456`).
+- Don't immediately evaluate output_only arrays when generating dzn output.
+- Coerce boolean objectives to integers.
+- Don't create copies of global declarations when creating par versions of
+ functions.
+- Compile infinite domains with holes into constraints (:bugref:`457`).
+- Use generic flattening inside generators, disallowing free boolean variables
+ inside ``in`` expressions (:bugref:`451`).
+- Strip library paths from includes in multi-pass compilation (:bugref:`455`).
+- Canonicalise file names of includes to ensure the same file is not included
+ multiple times.
+- Escape paths in printed ``include`` items, fixing backslash problems on
+ Windows.
+- Follow ids to declarations when flattening par arrays (:bugref:`448`).
+- Ignore par constants during chain compression.
+- Fix flattening of all-par set literals.
+
+Changes in the IDE:
+^^^^^^^^^^^^^^^^^^^
+
+- Fix possible crash due to incorrect use of WriteFile on Windows.
+- Ensure Gecode Gist dependencies are present in the Linux bundle and AppImage
+ (:idebugref:`132`).
+- Fix crash when stopping solver during exit.
+- Don't show irrelevant context menu entries in the project explorer.
+- Add support for HTTP/S links in the output pane.
+- Fix crash when saving CP Profiler executions where there is no info
+ associated with a node.
+- Show a warning when there are open files which are not part of a MOOC
+ submission.
+- Fix double spinbox precision issues (:idebugref:`134`).
+- Include Gecode Gist and CP Profiler dependencies in Snap package.
+- Allow opening of multiple files through the open file menu option.
+- Ensure file dialogs save last path when opening files.
+- Make the escape key close the find/replace dialog when focussed on any child
+ widget.
+- Allow setting MOOC submission items as mandatory.
+
+.. _v2.5.3:
+
+`Version 2.5.3 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 24 November 2020)
+
+Changes:
+^^^^^^^^
+
+- Fully reify -> (x != y) in the linear library.
+- Allow printing of comprehensions using introduced variables.
+- Allow increasing/decreasing over multidimensional arrays.
+- Add mzn_ignore_symmetry_breaking_constraints and mzn_ignore_redundant_constraints
+ options, allowing the symmetry_breaking_constraint and redundant_constraint
+ predicates to be overridden, so that those constraints can be disabled independent
+ of the solver library that's being used (:bugref:`429`).
+- Add automatic coercion of strings in JSON input data to enum constants where needed.
+- Add automatic coercion of lists in JSON input data to sets where needed.
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix int_lin_eq_imp in the linear library.
+- Use variable declaration location for invalid type-inst error messages without
+ locations.
+- Rewrite par versions of fzn_count_* into var versions, allowing solvers that
+ only redefine the bar version to use their built-in propagators even if the
+ value to count is fixed at compile time (:bugref:`427`).
+- Add multi-level array construction for enumerated types when outputting in
+ JSON format.
+- Ensure that functions can only be used as par if their return type is par
+ (:bugref:`431`).
+- Fix parser default location macro, preventing loss of location filenames
+ in some cases.
+- Fix parser rule for non-opt sets to give the correct starting location.
+- Fix fzn_bin_packing_capa_reif.mzn and fzn_bin_packing_load_reif.mzn
+ (:bugref:`435`).
+- Update decl for binary and unary operators when creating par versions of
+ functions (:bugref:`437`).
+- Only throw type errors for enum type identifier mismatch in strict enums mode.
+- Only post cumulative constraints if there is at least one task, preventing an
+ assertion about the lower bound from failing.
+
+Changes in the IDE:
+^^^^^^^^^^^^^^^^^^^
+
+- Only reset config window item focus if it is still focused, preventing spurious
+ changes in focus during code checking.
+- Fix handling of final statuses, including UNSAT (:idebugref:`123`).
+- Remove -s flag support from Gecode Gist solver configuration (:idebugref:`125`).
+- Fix crash when saving a project with no solver selected (:idebugref:`127`).
+- Correctly remove temporary parameter configuration files after use
+ (:idebugref:`128`, :idebugref:`129`).
+- Fix the time limit readout in the status bar when solving.
+
+.. _v2.5.2:
+
+`Version 2.5.2 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 6 November 2020)
+
+Changes:
+^^^^^^^^
+
+- Use full reification in int_ne_imp.
+- Add support for redefining 2d element constraints in the solver library.
+- Produce warning when shadowing a variable in a let or comprehension in the
+ same function (or toplevel) scope (:bugref:`419`).
+- Rewrite symmetric_all_different to inverse (:bugref:`426`).
+- Add link icons to globals etc in the reference documentation (:bugref:`425`).
+- Make the nodes statistic show the total number of nodes across all restarts
+ for SCIP.
+- Add support for multidimensional arrays in counting constraints (:bugref:`413`).
+- Allow .json files to be specified using the --data option (in addition to
+ .dzn files).
+- When specifying relative paths inside parameter configuration files,
+ resolve them relative to the config file.
+
+Bug fixes:
+^^^^^^^^^^
+
+- Correctly add file extension to plugin libraries when omitted.
+- Fix JSON array index coercion when the first index is undefined.
+- Catch ResultUndefined exception when evaluating cv par expressions,
+ and turn into undefined result.
+- Fix trailing for lets and comprehensions, resolving some issues with
+ recursive functions containing lets and/or comprehensions.
+- Only create par version of functions that do not refer to any toplevel
+ variables (:bugref:`418`).
+- Keep correct location information for identifiers.
+- Print warnings from solns2out.
+- Fix the removal of reverse mapped arrays when they contain aliases.
+- Disallow macro replacement when call has reification implementation.
+- Fix the behaviour of passing an invalid version hint to --solver.
+
+Changes in the IDE:
+^^^^^^^^^^^^^^^^^^^
+
+- Properly resize extra flags table after adding parameters (:idebugref:`119`).
+- Use the minimal configuration to check the model interface
+ (:idebugref:`118`).
+- Allow omitting builtin solver version in project JSON.
+- Don't mark as modified when loading non-synced solver configurations.
+- Ensure the last open configuration in a project is selected when loaded.
+- Fix the default values of solution truncation and output window clearing.
+- Process unrecognised extra flags from old project configurations.
+- Fix watching for modification of the additional data box.
+- Fix the alignment of line numbers.
+- Make behaviour controls more narrow to accommodate smaller window sizes.
+- Defocus config window widgets when updating solver config so values of
+ currently edited fields are updated.
+- Pass user input data correctly during compilation.
+- Remove solns2out options from MiniZinc call when compiling.
+
+.. _v2.5.1:
+
+`Version 2.5.1 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 22 October 2020)
+
+Changes:
+^^^^^^^^
+
+- Rewrite alldifferent_except_0 to fzn_alldifferent_except_0, to enable
+ solvers to implement that constraint if it is available (:bugref:`414`).
+- Propagate domains for variables even when reverse-mapped. This
+ ensures that variables with multiple encodings can be created with
+ the tightest possible bounds.
+- Fail instead of producing empty domains when simplifying int_le
+ constraints.
+- Allow parsing of nested objects in parameter configuration files.
+- Add --backend-flags option to provide a uniform way of passing flags
+ to an underlying solver.
+- Add extra flags support to the MIP solver interfaces, allowing
+ parameters to be set in the IDE.
+- Improve automatic detection of the Xpress solver and license file.
+- Allow the use of spaces in the --solver flag argument.
+- Automatically add the last part of the solver ID as a tag.
+- Improve handling of var functions in output, automatically creating
+ par versions of var functions if possible.
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix parsing of empty multidimensional JSON arrays.
+- Allow use of --parallel long form option in MIP solvers.
+- Fix item lookup when increasing annotation usage in annotate builtin.
+- Fix JSON array coercion to handle arrays with 1 unknown index.
+- Don't try to access array dimensions for output of empty
+ multi-dimensional arrays.
+- Print verbose version information to stderr instead of stdout.
+- Fix context handling when flattening par expressions that contain
+ variables (:bugref:`415`).
+- Flatten string expressions if they contain variable parts in
+ assert/abort/trace calls.
+- Fix breakage on older versions of Windows due to UTF-8 conversion
+ failing.
+- Remove defines_var/is_defined_var annotations when simplifying
+ boolean constraints.
+- Fix transfer of cv status from where parts to newly generated
+ conjunctions during typechecking.
+- Fix multiple issues with the defined_var / is_defined_var
+ annotations.
+- Move all included files from stdlib into solver_redefinitions.mzn, so
+ that solver redefinitions are not marked as belonging to the standard
+ library (:bugref:`416`).
+- Fix documentation group for standard annotations (:bugref:`417`).
+- Show correct version of solver plugins which have their DLLs
+ specified using a command-line parameter (:bugref:`411`).
+- Fix arbitrary flag support for NL solvers.
+- Kill child processes if exception occurs during solns2out on
+ Unix-like platforms.
+
+Changes in the IDE:
+^^^^^^^^^^^^^^^^^^^
+
+- Fix typo when passing solver statistics option to minizinc (:idebugref:`112`).
+- Fix missing statistics output (:idebugref:`112`).
+- Add support for colour themes (:idebugref:`110`).
+- Don't prompt for saving after adding/removing files from the Untitled
+ project.
+- Fix running of compiled FlatZinc files.
+- Show error message when trying to load an invalid configuration file.
+- Ensure all output is sent to the output console, and that fragments
+ in standard error output appear when a newline is written to standard
+ output (:idebugref:`114`).
+- Fix running of solver configurations from the project explorer.
+- Improve performance of adding a large number of extra flags at once.
+- Add support for 64-bit integer extra flags.
+- Add support for setting both solver backend flags and MiniZinc
+ command flags (:idebugref:`113`).
+- Improve interface for adding extra parameters, allowing search/filter
+ and multiselection of known parameters.
+
+.. _v2.5.0:
+
+`Version 2.5.0 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 6 October 2020)
+
+Language, tool and library changes:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Allow `reading command line arguments from JSON config
+ file `__.
+- Add support for `enum
+ constructors `__.
+- Put subprocesses in their own process group so that they don't
+ receive signals from both the console and MiniZinc.
+- Implement soft and hard process timeouts on Windows, allow triggering
+ of shutdown from named pipe on Windows for the IDE.
+- Make MiniZinc unicode-aware on Windows.
+- Better error messages for index set mismatches.
+- Report similar identifiers when matching fails.
+- Better error messages when a call cannot be matched to an existing
+ function or predicate.
+- Print error stack if top of stack is a single identifier (i.e., error
+ occurred while flattening a variable declaration).
+- Add new separate flags for intermediate and all solutions. -i enables
+ intermediate solutions for optimisation problems and
+ --all-satisfaction enables all solutions for satisfaction problems.
+
+Changes in interfaces to solvers:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Solvers which only support intermediate solutions now can now support
+ the standard flag -i rather than -a.
+- Restructure the `MiniZinc standard
+ library `__.
+
+Changes in MIP solver backends:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Remove non-conforming -n flags for MIP solver configs standard flags.
+- Improve autodetection of Gurobi DLL.
+- Find Gurobi 9.0.2 when building.
+- Don't create gurobi log.
+- Interface to concurrent solves in Gurobi (--readConcurrentParam).
+- Add -DMinMaxGeneral option for min/max as fzn_array_float_minimum for
+ Gurobi
+- Find SCIP 7.0 on Windows
+- Use -Glinear library, built-in cumulative by default for SCIP.
+- Use quadratics in Gurobi and SCIP by default.
+- Add options --xpress-root and --xpress-password for finding Xpress
+ installation directory and licence file.
+- Add MIQCP quadratic constraints for Gurobi and SCIP.
+
+Changes dealing with option types:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Add opt versions of several globals.
+- Define weak equality for var opt bool.
+- Add set_in definitions for var opt int.
+- Add opt versions of enumerated type functions (to_enum, enum_next,
+ enum_prev etc).
+- Enable set literals with optional values (which will be ignored),
+ including var set literals with var opt int elements.
+- Add opt version of float_dom to stdlib.
+- Change unary not for opt bool to use absorption lifting.
+- Add array2set functions on var opt int arrays.
+- Add opt versions of dom, dom_array and dom_bounds_array.
+- Add missing logical operators to var opt bool.
+
+Changes in the MiniZinc IDE:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Remove support for the old binary storage format of projects. These
+ must be opened and re-saved with version 2.4.3 to remain compatible.
+- Include experimental CP-profiler through the \*MiniZinc\* > \*Profile
+ search\* option for supported solvers.
+- Redesign the solver configuration window.
+- Use parameter configuration files rather than passing command-line
+ options directly.
+- Show solver configurations and checkers in their own sections in the
+ project explorer.
+- Allow multiselection in the project explorer for running particular
+ sets of files.
+- Allow MiniZinc to manage subprocesses by itself.
+- Allow non-privileged installs of the IDE on Windows.
+- Correctly remove files from old installations of the IDE on Windows.
+- Enable scroll bars in the preferences dialog to allow for low
+ resolution displays.
+- Prompt to save modified files before performing MOOC submissions or
+ running models.
+- Fix infinite recursion when a model file for a MOOC submission
+ doesn't exist.
+- Use --output-mode checker for MOOC solution submission where
+ supported.
+- Fully support unicode on Windows.
+
+Minor changes:
+^^^^^^^^^^^^^^
+
+- Clean up code base and format using clang-format and clang-tidy.
+- Update WebAssembly build for new versions of emscripten.
+- Support --cp-profiler option to activate search profiler for IDE.
+- Add --solver-json to output single solver config as JSON.
+- Coerce JSON arrays to match the MiniZinc TypeInst.
+- Add more informative README file.
+- Split shared MIP cpp code into seperate CMake object target.
+- Compile with POSITION_INDEPENDENT_CODE targets by default.
+- Change ASTString to use String Interning.
+- Add included_files output to model interface.
+- Update Bison parsers to be compatible with Bison 3.7.
+- Allow annotating enum declarations.
+- Add support for --c_d and --a_d options to set recomputation
+ commit/adaption distance for Gecode presolver.
+- Place float_set_in in a version redefinition documentation group.
+- Place int_pow_fixed into a version redefinitions group.
+- Move set_in(var int, set of int) to the Integer FlatZinc Builtins.
+- Make "show" display contents of arrays rather than array identifiers
+ if the array is var
+- Add support for checking statistics after solving has finished.
+- Include preferences set by IDE repository.
+- Add has_ann(var, ann) annotation introspection builtin.
+- Use reverse mapped version for output if FlatZinc contains an aliased
+ variable.
+- Remove NDEBUG flag from the compile flags added by CPLEX and Gurobi.
+- Use integer variables in decomposition for array_int_element,
+ array_var_int_element, array_int_minimum, and array_int_maximum.
+- More preprocessing for pow(int, int).
+- Add is_same builtin.
+- Add multiobjective annotation for Gurobi and Yuck (in
+ std/experimental.mzn).
+- Add --output-mode checker, which outputs exactly the variables that
+ are required for a given solution checker.
+- Improve propagation of annotations, especially for redefined forall,
+ exists, clause, xor
+- Make omitting RHS from output_only variable a type error.
+- Add support for var set comprehensions
+- Make sets inside set literals a type error (rather than evaluation
+ error).
+- Aggregate bool_not into exists/clause, use bool_not(e) for
+ clause([],[e]) expressions
+- Cleanup the common-subexpression elimination table.
+- Generate bool_not calls (instead of bool_eq_reif) and add both "x=not
+ y" and "y=not x" into the CSE map, to avoid double negations.
+- Add arg_max and arg_min builtins for boolean arrays.
+- Remove -O flag from ozn file naming.
+- Allow var items in checkers to be omitted from the model.
+- Add builtins for binary operators that have a var redefinition.
+- When an integer or bool variable has a singleton domain, use the
+ value. This enables more overloading to par functions.
+- Check if domain becomes empty when binding variable to value,
+ avoiding empty domains (such as 1..0) in FlatZinc.
+- Ignore unknown JSON data items instead of throwing an error.
+- Add trace_logstream and logstream_to_string builtins. These can be
+ used for writing model checkers/graders, but also for general
+ logging.
+- Clean up CMake configuration
+- Allow any installed solver to be used with the test suite, add
+ ability to test for expected ozn output.
+
+.. _bug-fixes-1:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix error message for type errors in domains that are integer
+ literals (:bugref:`408`).
+- Fix comprehensions over option types, which could cause crashes and
+ incorrect flattening (:bugref:`407`).
+- Fix the usage count of annotations added using the annotate function
+- Flatten "in" expressions in comprehensions when required.
+- Check if operator is built-in after evaluating arguments, to make
+ sure it is rewritten into the correct predicate.
+- Use dom(x) instead of lb(x)..ub(x) for opt int.
+- Use eval_par to compute bounds for par expressions since they might
+ be opt.
+- Use library defined operators where available.
+- Fix -O flag parsing for optimisation level.
+- Fix par set inequality calculation.
+- Flatten domain expressions that contain variables.
+- Catch ResultUndefined when flattening an array with an undefined
+ expression in a generator
+- Fix source paths in MD5 generation scripts.
+- Fix crash when reporting undefined result in assignment generator.
+- Only add coercion for normal generators, not for assignment
+ generators.
+- Check output var status on actual item being removed.
+- Include absolute path instead of filename in multipass processing.
+- Coerce comprehension generators if necessary, so that slicing
+ notation can be used there.
+- Fix copying of comprehensions with followIds.
+- Fix the method signature of printStatistics for Geas.
+- Ensure the definition of reverse mappers are copied into the output
+ model.
+- Print solns2out statistics to stdout to comply with MiniZinc spec.
+- Minor doc-fix for global_cardinality_closed.
+- Make statistics output comply with MiniZinc spec.
+- Fix reverse function to work with empty arrays
+- Fix the coercion of boolean sum in aggregation.
+- Remove eval_par on var expressions in show builtin.
+- Fix the table construction for the Geas solver interface
+- Fixed wrong sign in Boolean linear constraints in Geas solver
+ interface.
+- Fix istrue and isfalse by using flat_cv_exp if necessary.
+- Fix the excess flattening of items marked for removal.
+- Do not add newline to output when killing FlatZinc solver process,
+ since this may be in the middle of a line
+- Fix typo in loop for Geas solver instance.
+- Don't call doAddVars when there are no variables, fixing a crash in
+ MIP solvers for empty models.
+- Do not copy type of lhs onto rhs when parsing solutions. This tagged
+ some literals as cv(), which broke the evaluation.
+- Fix flattening of all par set literals.
+- Fix error macro to be compatible with newer versions of Bison (:bugref:`389`).
+- Fix printing of if-then-else expressions without an else branch.
+- Fix allowed solvers option in test suite.
+- Make bind only create an int_eq constraint if a variable has a
+ reverse mapper.
+- Fix automatic coercions to keep cv type attribute of their argument
+ (:bugref:`387`).
+- Fix copying of output_only variables to the output model.
+- Only print checker output for unique solutions.
+- Fix rewriting of lin_exp into int/float_lin_eq.
+- Fix flattening of calls and let expressions that have par type but
+ contain var expressions.
+- Use eval_bool instead of eval_par for boolean evaluation.
+- Remove the direct assignment to a domain if it has a reverse mapper.
+- Fix arg_max and arg_min for array index sets not starting at 1.
+- Add missing set_superset_reif FlatZinc predicate.
+- Fix counting of non-fixed variables in Boolean constraints. Could
+ previously lead to incorrect simplifications.
+- Enable eval_floatset for SetLits that contain an IntSetVal. This is
+ used during chain compression and could previously result in
+ incorrect domains.
+- Fix bugs in chain compressor caused by modifying multimaps while
+ iterating over them.
+- Fix crash when cleaning up after running builtin Gecode.
+- MIPdomains: don't assume equations have no literals.
+- Only fix domain after flattening bool_eq.
+- Only return singleton domain as value for non-optional variables.
+- When evaluating identifier that is bound to a fixed value, check that
+ the value is inside the domain to correctly detect model
+ inconsistency.
+- Add missing assert and trace builtin overloads.
+- Flatten expressions that may contain variables in par where clauses.
+- Fix segmentation fault when the declaration of an array is passed to
+ setComputedDomains with the -g parameter.
+- Consider single-valued domain variables to be fixed
+- Add missing definition of to_enum for arrays of sets.
+- Evaluate partiality of arguments even if call was already in CSE
+ table (:bugref:`374`).
+
+.. _v2.4.3:
+
+`Version 2.4.3 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 4 March 2020)
+
+.. _changes-1:
+
+Changes:
+^^^^^^^^
+
+- Enable CPLEX 12.10.
+- Add checker output to generated output items.
+- Short-circuit evaluation for mixed par/var conjunctions,
+ disjunctions, and clauses.
+- Add inverse_in_range global.
+- Pretty printing set ranges now uses union instead of ++ to be
+ compatible with DZN.
+- Add array2set for par bool and float arrays
+- The \_objective variable is no longer added to FlatZinc input files.
+- JSON representation of sets with ranges can now be parsed (previously
+ they could only be output).
+- Check index sets to arguments of global_cardinality_low_up.
+- Xpress and SCIP are not compiled as plugins and no longer require
+ recompilation to enable.
+- If-then-else for opt are no longer written in terms of the non-opt
+ version, allowing them to return absent.
+
+.. _bug-fixes-2:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix checking of domains and index sets in par arrays inside lets.
+- Remove duplicate call stack items to improve error messages.
+- Ignore absent values when computing domains.
+- Generate call for actual binary operator (after optimising double
+ negation). Fixes :bugref:`364`.
+- Fix non-associative operators on optional values.
+- Only output optional parameters in model interface if they were
+ undefined (rather than assigned to <>).
+- Fix some issues with evaluating par opt expressions.
+- Make solution checkers work for multi-dimensional arrays and arrays
+ with enum index sets
+- Fix Boolean aggregation for expressions that are defined recursively.
+- Use correct index set for nosets set_lt and similar (partial fix for
+ :bugref:`369`)
+- Fix coercion of sets to arrays (previously, coercing a set of X to an
+ array of X to an array of Y did not work correctly).
+- Fix infinite loop when printing infinite set range
+- Add assertion so that array2set can only be used for arrays with
+ bounds (:bugref:`370`, :bugref:`371`).
+- Fix typing and pretty printing of par bool sets.
+- Use output_array dims for output vars in FlatZinc files (previously,
+ a type-checker error would occur when running a solver through
+ MiniZinc on a FlatZinc file with multidimensional arrays).
+- The Xpress backend was made functional again.
+- Fix segmentation fault in output_only type-checking.
+- Compute correct array enum type for array slices (:bugref:`372`).
+- Fix behaviour of using undefined expressions in var comprehensions
+ guarded against by where clauses (previously, these undefined
+ expressions would bubble up regardless of the where clause,
+ constraining the model).
+- IDE: Disable menu items that don't make sense when all tabs are
+ closed, fix behaviour of stop button when all tabs closed (fixes
+ several crashes).
+- IDE: Add x86_64 suffix to linux package name (:idebugref:`96`).
+- IDE: Make boolean extra solver options with a default of true
+ functional.
+- IDE: Only read linter results if it exited normally (:idebugref:`97`).
+- IDE: Resolve paths in \_mooc to paths (allowing submission of models
+ in subdirectories).
+
+.. _v2.4.2:
+
+`Version 2.4.2 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 10 January 2020)
+
+.. _changes-2:
+
+Changes:
+^^^^^^^^
+
+- The test suite is now integrated into the continuous integration
+ system.
+
+.. _bug-fixes-3:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix flattening of negated disjunctions (:bugref:`359`).
+- Fix simplification of Boolean constraints (repeated simplification
+ could sometimes crash).
+- Fix memory management during flattening of conditionals (:bugref:`358`).
+- Fix type inference for rewriting of sums into count constraints, and
+ only apply the rewriting for var type-insts.
+- Fix handling of solution checkers (these used to produce spurious
+ error messages).
+- IDE: Fix syntax highlighting of keywords, and add syntax highlighting
+ for interpolated strings.
+- IDE: Redraw when switching to/from dark mode, and fix dark mode
+ header colours.
+- IDE: Fix "Select all" menu item.
+
+.. _v2.4.1:
+
+`Version 2.4.1 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 20 December 2019)
+
+.. _changes-3:
+
+Changes:
+^^^^^^^^
+
+- Improve compiler optimisation for some linear, multiplication and
+ Boolean constraints.
+- Improved translation of lex and all_equal constraints when the arrays
+ have no or only one variable.
+- IDE: Display error message when submission to MOOC provider fails.
+- IDE: Make "previous tab" and "next tab" actions cycle rather than
+ stop at first/last tab.
+
+.. _bug-fixes-4:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fixed regular expression constraint for expressions containing
+ negated character classes (^ operator).
+- Fix element constraint in nosets.mzn library when set domains are not
+ contiguous.
+- Correctly identify Windows paths starting with // or \\\\ as absolute
+ (this enables the parser to open files stored on network drives).
+- Use set_in constraints (rather than int_in) for internal Gecode-based
+ presolver. This fixes some issues when compiling with -O3.
+- The optimisation phase of the compiler now fully substitutes par bool
+ variables (these can be introduced into the FlatZinc during multipass
+ compilation). (:bugref:`357`)
+- Fixed the reference counting for variables that are re-used in
+ multipass compilation. (:bugref:`357`)
+- Remove incorrect error handling when parsing from strings rather than
+ files. Partially fixes (:bugref:`357`)
+- Made the is_fixed builtin work for more types. (:bugref:`356`)
+- Enable rewriting of sum(i in x)(i=c) op d and count(x,y) op z into
+ global counting constraints.
+- Split up count global constraints into separate files for reified
+ versions.
+- Use contiguous range for array index set in set_lt for nosets.mzn.
+- Negate results of conditionals if required. (:bugref:`355`)
+- Partiality of conditional needs to be translated in root context
+ (even if conditional itself is negated). (:bugref:`355`)
+- Don't copy function into output again if it was already copied (and
+ made par) before. (:bugref:`323`)
+- Define card function on var sets in terms of set_card FlatZinc
+ builtin.
+- Don't set bounds for set variables in internal Gecode presolver.
+- IDE: Fix shift left and shift right indentation behaviour when
+ selecting text backwards.
+- IDE: Fix OpenSSL library in binary distribution to enable update
+ checks and submission to MOOCs again.
+
+.. _v2.4.0:
+
+`Version 2.4.0 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 13 December 2019)
+
+.. _changes-4:
+
+Changes:
+^^^^^^^^
+
+- The compiler now detects counting constraints in expressions such as
+ count(i in x)(i=3) <= 4 and rewrites them into global counting
+ constraints. This is now the preferred way to specify counting. The
+ atmost/atleast/exactly constraints on integer variables have been
+ deprecated, and versions of count predicates with par variables have
+ been added. FlatZinc solvers that supported atmost/atleast/exactly
+ should now support the corresponding fzn_count_?_par predicates.
+- The compiler now supports the command line option
+ --output-detailed-timing, which provides timing information for each
+ toplevel constraint item, or for each line of code when used in
+ conjunction with the --keep-paths option.
+- The library now contains annotations for deprecated library
+ functions.
+- A par version of the inverse function has been added (include
+ inverse_fn.mzn to use it).
+- The common case of sums of optional variables is now handled more
+ efficiently. This case often arises from generator expressions with
+ variable where clauses.
+- Added set_to_ranges built-ins to enable efficient iteration over
+ sets. These are used to implement set_in for float variables, which
+ was missing before.
+- The Gurobi and CPLEX backends now support the --random-seed command
+ line option.
+- The Gurobi and CPLEX backends now use nodefile for search trees
+ exceeding 500 MB (--nodefilestart can change this value and
+ --nodefiledir the folder.)
+- The MIPDomains optimisations have been switched back on by default.
+ The optimisations have also been strengthened for some special cases.
+- Without the MIPdomains postprocessing, linearisation of variable
+ domains with holes now uses set_in instead of individual not-equal
+ constraints, which may result in more compact FlatZinc.
+- Linearisation of multiplication can now consider the exact domain of
+ a factor.
+- The product functions have been made non-recursive in order to
+ support longer arrays.
+- Bounds inference for results of if-then-else expressions has been
+ improved.
+- Support for optional float variables has been added.
+- The interfaces to CBC, CPLEX and Gurobi now report correctly that
+ they support verbose output during solving (so that the "verbose
+ solving" option is available from the MiniZinc IDE).
+- IDE: Parse timing and statistics output produced by compiler, and
+ display as profiling information next to each line in the model.
+- IDE: Enable run/compile action on data files. This automatically
+ selects the model file if there is only one, or presents a dialog for
+ selecting the model if there are multiple.
+- IDE: Select first data file in parameter dialog if there was no
+ previous selection, and always focus parameter dialog.
+- IDE: Highlight current line.
+- IDE: Support .json as file extension for data files.
+- IDE: Remember whether wrap around, case sensitivity and regular
+ expression was selected in find/replace dialog, pre-select the
+ find/replace text when find/replace widget is openend, and close
+ find/replace widget when ESC is pressed while editor has focus.
+
+.. _bug-fixes-5:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fixed output handling on Windows (output is now processed on the main
+ thread, so that exceptions thrown during output are printed
+ correctly, and memory management is thread safe).
+- Fixed decomposition of reified mdd constraint, and strengthened
+ decompositions of mdd and cost_mdd.
+- Fix handling of variable re-definitions (e.g. converting sets to
+ arrays of bools), which would previously sometimes result in
+ variables being removed although they were required for output, or
+ the reverse mapping function not being available in the output model.
+- Include regular.mzn from regular_regexp.mzn. (:bugref:`351`)
+- Inlining of function calls has been moved from the flattener into the
+ type checker, and it now is more strict about which functions can be
+ inlined in order to avoid overloading issues.
+- Updated fzn_count_{neq,leq,lt,geq,gt},
+ fzn_global_cardinality_low_up{,_reif} to use use the count_eq
+ predicate. (:bugref:`334`, :bugref:`335`)
+- Fixed the documentation for several constraints, which did not
+ display as bullet point lists as intended.
+- Copy function/predicate declarations into FlatZinc without
+ annotations, since most FlatZinc parsers would not expect annotations
+ and fail to parse.
+- Process right hand side of par VarDecls to make sure any identifiers
+ it uses are copied into the output model. Fixes :bugref:`336`.
+- Fix type checking for conditionals where the else branch has enum
+ type but the then branch has int type.
+- Make the deopt function return correct enum instead of int type.
+- Fix for path handling when 'needRangeDomains' is active. Avoids
+ infinite recursion in the compiler.
+- Fix race condition in temporary file generator for Windows. (:bugref:`349`)
+- Register fzn\_ names for Gecode presolver. Fixes command line flags
+ -O3 and above.
+- Fix par evaluation of float and bool set comprehensions.
+- Fix documentation of array_bool_xor. Fixes :docbugref:`13`.
+- Fix the round() built-in to correctly round negative numbers
+- Fix computation of intersection of domains when assigning an array to
+ an array variable. Fixes :bugref:`310`.
+- Add defines_var annotations for functional global constraints. Fixes
+ :bugref:`345`.
+- Add set_lt_reif/set_le_reif to flatzinc builtins library. Fixes :bugref:`338`.
+- Clarify set order based on spec. Fixes :bugref:`339`.
+- Don't return already removed VarDecl objects from CSE. Fixes :bugref:`346`.
+- Do not post y!=0 constraint if 0 is not in the domain (workaround for
+ a limitation in the handling of basic float constraints). Fixes :bugref:`344`.
+- Help type checker by making deopt/occurs argument types explicit.
+ Fixes :bugref:`331`.
+- Fix transfer of domains when aliasing one variable to another
+- MIP: fix for aux_float_ne_if_1
+- MIP: int_(eq/ne)_imp: don't force eq_encode without MIPdomains
+- Fix a typo in the definition of fzn_at_least_int{,_reif}
+- Fix dependency problem in the gecode_presolver table specification
+- Add seq_precede_chain.mzn to globals.mzn. Fixes :bugref:`332`.
+- Don't assign right hand side of set variables if domain is singleton.
+ Fixes :bugref:`330`.
+- Don't invalidate float bound just because an expression contains an
+ integer.
+- Fix copying of let expressions.
+- Put lexer and parser helper functions into MiniZinc namespace to
+ avoid linker issues. Fixes :bugref:`325`.
+- Reset array index sets defined in lets inside recursive function
+ calls.
+- Arrays copied into output model need to have par type-inst. Fixes :bugref:`322`.
+- Don't complain when same function is registered twice. Fixes :bugref:`323`.
+- Fix partiality handling of if-then-else expressions.
+- Track whether variable is used in an output array before making
+ decision to compress implication chains. Fixes :bugref:`318`.
+- IDE: Fix dark mode detection on macOS 10.15, improve dark mode colors
+ a bit and fixed some dark mode bugs.
+- IDE: Make background compilation of a model (used to display syntax
+ and type errors) a bit more stable.
+- IDE: Avoid infinite loop in wrap around replace all.
+- IDE: Fix memory management for HTML visualisation windows, and resize
+ docked HTML visualisation widgets to take up equal space.
+
+.. _v2.3.2:
+
+`Version 2.3.2 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 12 September 2019)
+
+.. _changes-5:
+
+Changes:
+^^^^^^^^
+
+- Add warm starts and subtour cuts to CBC interface.
+- Add documentation and assertion requiring that mdds are
+ deterministic, and add nondeterministic variant of mdd constraint.
+- Add -s to the standard flags supported by MIP interfaces.
+- Add flag --output-output-item to include user specified output item
+ in the formatted JSON and DZN output.
+
+.. _bug-fixes-6:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug that could leave unused variables in the resulting
+ FlatZinc.
+- bounded_dpath should rewrite to fzn_bounded_dpath. Fixes :bugref:`300`.
+- Fix definition of sum_set.
+- Check if overloaded function required for output. Fixes :bugref:`303`.
+- Move regular constraint with set argument to its own file.
+- Flatten assignment generators if necessary.
+- Simplify fzn_value_precede_chain_int and avoid use of element
+ predicate. Fixes :bugref:`307`.
+- Only initialise par opt variables as absent if they are not arrays.
+- Fix the description of the neural_net predicate.
+- Fix regular constraint with regular expressions (stopped working in
+ 2.3.0).
+- Fix the model interface output to include the same variables as the
+ generated output statement.
+- Fix CSE for removed variable declarations. Could lead to reified
+ constraints not being compiled correctly when the control variable
+ got fixed to true.
+
+.. _v2.3.1:
+
+`Version 2.3.1 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 10 July 2019)
+
+.. _bug-fixes-7:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Report error when trying to assign an array literal to an array
+ variable with incompatible index set.
+- Fix partial evaluation of expressions, so that only par expressions
+ are fully evaluated. Fixes :bugref:`298`.
+- Remove carriage returns when reading piped solver output on Windows.
+- Canonicalize paths of executables to avoid spurious warnings about
+ multiple executables for the same solver.
+- Add implementations for != on arrays.
+- Compute quotient bounds before decomposition of int_div in
+ linearisation library.
+- Propagate domain constraints on variables that are aliased
+ (previously domain constraints could get lost).
+- Propagate domain constraints from left-hand-side to right-hand-side
+ in variable assignments.
+- piecewise-linear: reuse decomposition for X when only Y-values
+ change.
+- nosets: add set_in_imp(var set) and simplify set_in_reif, set_eq(var
+ set, var set).
+- linearisation: improved compilation of set_in constraints.
+- MiniZinc IDE: Remove incorrect symbolic link and fix qt.conf for some
+ bundled distributions.
+- MiniZinc IDE: Fix check for availability of dark mode on older
+ versions of macOS.
+- MiniZinc IDE: Fix a typo in the cheat sheet.
+- MiniZinc IDE: Provide more robust solution for checking the model
+ parameters, which will get rid of some "internal error" messages.
+- MiniZinc IDE: Always show directory selection dialog in the Windows
+ installer. Addresses :idebugref:`89`.
+- MiniZinc IDE: Improved the configuration files for some bundled
+ solvers, provides nicer configuration interface.
+
+.. _v2.3.0:
+
+`Version 2.3.0 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 26 June 2019)
+
+Major changes:
+^^^^^^^^^^^^^^
+
+- The compiler can now generate FlatZinc with half reified constraints.
+ See
+ https://www.minizinc.org/doc-2.3.0/en/fzn-spec.html#reified-and-half-reified-predicates
+ for more details.
+- The standard library of global constraints has been reorganised,
+ making it easier for solvers to override just the bits that they
+ support. See
+ https://www.minizinc.org/doc-2.3.0/en/fzn-spec.html#solver-specific-libraries
+ for more details.
+- There is experimental support for solvers that can read AMPL NL
+ files. See
+ https://www.minizinc.org/doc-2.3.0/en/solvers.html#non-linear-solvers
+ for details.
+
+.. _minor-changes-1:
+
+Minor changes:
+^^^^^^^^^^^^^^
+
+- The JSON input and output has been improved, with full support for
+ enums and optional types.
+- A new compiler option -g has been added, which turns variable domain
+ changes into constraints (useful for debugging models).
+- The SCIP interface has been updated, with support for indicator
+ constraints, bounds disjunctions and a native cumulative constraint.
+- Error reporting has been improved, with location information
+ available for errors in par float expressions as well as include
+ items.
+- The timeout command line parameter now also applies to compilation
+ itself (:bugref:`281`).
+- Operations on par float values are now checked for overflows.
+- The arg_min/arg_max constraints have been improved, with new special
+ versions for Boolean variables, and a better standard decomposition.
+- if-then-else-endif expressions with variable conditions are now
+ compiled to a predicate call (rather than handled by the compiler),
+ which enables solver libraries to implement these as native
+ constraints or special decompositions.
+- Dividing a variable by a constant is now translated as a
+ multiplication (to keep the constraints linear).
+- A new piecewise_linear predicate has been added to the library to
+ make it easier to specify piecewise linear constraints.
+- Print number of solutions as mzn-stat after solving (:bugref:`244`).
+- Make search annotations work for arbitrary array index sets.
+- MiniZinc IDE: The IDE will now check MiniZinc code for syntax and
+ type errors, and the editor performs simple code completion for
+ MiniZinc keywords
+- MiniZinc IDE: The find/replace dialog is now an inline widget and
+ supports incremental search.
+- MiniZinc IDE: Now supports dark mode on macOS.
+- MiniZinc IDE: Add support for extra solver flags (parsed from solver
+ configuration).
+
+.. _bug-fixes-8:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Translate let expressions that contain constraints or variables as
+ var type-inst. Fixes :bugref:`263`.
+- Fix JSON array parsing by counting elements instead of commas.
+- Fix parsing of the -p flag (:bugref:`271`).
+- Fix type checking for array declarations with single enum type inst
+ identifier. E.g. array[$$T] of $U previously matched any
+ multi-dimensional array, and now only matches one-dimensional arrays
+ with any enum index set.
+- Fix computation of function return type when using type inst
+ variables (:bugref:`272`).
+- Evaluate each variable declaration only once in a par let expression.
+- Check domain constraints on variable declarations in par let
+ expressions.
+- Try .exe/.bat on windows when using (constructed) absolute paths.
+- Fix array slicing to support empty slices (:bugref:`275`).
+- Fix a bug in the parser that could cause crashes on certain syntax
+ errors.
+- Fix the type of bool2int for arrays.
+- Initialise counter for introduced variable ids based on names in
+ original model. This avoids reusing variable names if the user model
+ contains names such as X_INTRODUCED_0_.
+- Fix compilation of nested clause/exist constraints, and improve
+ handling of negation. Tries to use primitive negation instead of
+ creating negated constraints. Should help with half-reification by
+ creating more positive contexts.
+- Reorder fields in basic data structures to reduce padding on 64 bit
+ platforms (improved memory footprint).
+- Perform type coercion after desugaring array slicing.
+- Translate arguments to bool2int, exists, forall in positive context
+ even if those functions are redefined.
+- Don't evaluate par array literals twice (inefficient, and can lead to
+ incorrect results when using random number generators).
+- Terminate child processes when minizinc process is terminated by
+ signal.
+- Fix function return value array index check for empty arrays (:bugref:`286`).
+- Fix translation of constant false where clause in array
+ comprehension.
+- Report error when json multi-dimensional array is not rectangular.
+- Check index sets of function arguments (:bugref:`273`).
+- Ignore partiality variables from CSE table when compiling \_reif and
+ \_imp predicates (:bugref:`269`).
+- Flatten comprehensions with variable generators or where conditions
+ before evaluating any par functions on them (:bugref:`259`).
+- Add missing redefinitions of basic operators and search annotations
+ for optional integers.
+- Resolve filenames given on the command line relative to working
+ directory, and warn if file in working directory has same name as
+ included file from the library. Fixes :bugref:`276`.
+- Update nosets library with a valid redefinition of set_less over
+ booleans.
+- Fix translation of showJSON (:bugref:`294`).
+- Only apply set2array coercion for supported types, otherwise report
+ error (:bugref:`295`).
+- Improve special case reasoning for abs on strictly negative
+ variables.
+- Add bounds for floating point min/max result in the standard library.
+- MiniZinc IDE: Ensure cursor is visible (editor scrolls to cursor
+ position) when pressing tab or enter. Fixes :idebugref:`71` :idebugref:`71`.
+- MiniZinc IDE: Re-dock configuration editor when closing un-docked
+ window.
+- MiniZinc IDE: Handle quotes when parsing additional solver command
+ line arguments. Fixes :idebugref:`77`.
+- MiniZinc IDE: Add workaround for the missing libnss requirements.
+ Fixes :idebugref:`79`.
+- MiniZinc IDE: Allow spaces in $DIR in MiniZincIDE.sh Fixes :idebugref:`81`.
+
+.. _v2.2.3:
+
+`Version 2.2.3 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 31 October 2018)
+
+.. _bug-fixes-9:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix some typos in the library documentation.
+- Fix solution checking.
+- Fix line numbers in parsed locations on 64 bit platforms.
+- Fix bounds computation for calls.
+- Fix translation of var where clauses with more than 3 par components.
+- IDE: Only run solution checker if it is enabled in the solver
+ configuration dialog.
+
+.. _v2.2.2:
+
+`Version 2.2.2 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 26 October 2018)
+
+.. _changes-6:
+
+Changes:
+^^^^^^^^
+
+- Some changes to the optimisation phase of the compiler, to take into
+ account more variables and constraints.
+- Preliminary support for MIP cuts based on graph algorithms (only
+ available when compiled with boost C++ libraries; not part of the
+ binary distribution).
+- Set Release as default build type when nothing is specified (for
+ CMake platforms that do not support multiple build types, like
+ Makefiles).
+- Add builtins outputJSON() and outputJSONParameters() for creating an
+ array of strings that capture the output and parameters of the model
+ as JSON.
+- On Linux and macOS, add /usr/share/minizinc/solvers and
+ /usr/local/share/minizinc/solvers to list of paths where solver
+ configuration files can be placed.
+- Add OSICBC_INCLUDEDIR and OSICBC_LIBDIR cmake flags.
+- Output search paths for solver configurations using --solvers command
+ line option.
+- Add support for Gurobi 8.1
+- Support parsing from stdin and files at the same time.
+- IDE: Add line/column display in status bar.
+- IDE: Optional parameters don't have to be defined in input dialog.
+- IDE: Provide mzn-json-init / mzn-json-init-end handlers to initialise
+ HTML window before first solution is produced.
+- IDE: Add version information and minimum system version into
+ Info.plist on macOS.
+- IDE: Manage multiple open visualisation windows, and implement
+ re-solve function that can be initiated from a visualisation.
+- Binary bundle: Gecode updated to version 6.1.0, Chuffed updated to
+ version 0.10.3
+
+.. _bug-fixes-10:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix crash when flattening top-level array comprehensions with var
+ where clauses.
+- Support input files with more than 1M lines.
+- Special case handling for array literals in top-level foralls:
+ flatten in root context.
+- Fix translation of if-then-else for branches with undefined right
+ hand sides.
+- Only propagate defines_var annotation to the variable that's actually
+ being defined (not others that arise from the same decomposition).
+- Don't flatten arguments of predicates like
+ symmetry_breaking_constraint.
+- Remove output_var and output_array annotations from user models
+ (these could cause crashes).
+- Fix precedences for weak operators (~+, ~-, ~=, ~*).
+- Fix min and max for opt var arrays to work when the bounds of the
+ arrays are unknown.
+- Fix a bug in bounds computations for function calls.
+- Add missing superset FlatZinc builtin.
+- Fix includes in file values.hh for some platforms.
+- Fix a garbage collection issue when printing solutions.
+- Deal with the case that a variable that's required for output is
+ assigned to a par variable.
+- Throw type error when an array has only absent values.
+- Flatten all arrays in FlatZinc, also those coming from functional
+ definitions.
+- Use list of strings as mzn_solver_path entry in the preferences json
+ file.
+- Fix crash when output variable is defined using recursive function
+- IDE: Fix race condition in constructor of HTMLWindow.
+
+.. _v2.2.1:
+
+`Version 2.2.1 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 6 September 2018)
+
+.. _changes-7:
+
+Changes:
+^^^^^^^^
+
+- all_different, all_equal, {int,set,float,bool}_search now accept
+ multi-dimensional arrays.
+- Add exponentiation operator (^).
+- Improve layout of generated library documentation for some
+ constraints.
+- Relax typechecking to allow assignment of empty array ([]) to
+ multi-dimensional array variables. This is required to make empty
+ arrays work in JSON data files.
+- Enumerated types can now be initialised using lists of strings. This
+ enables enumerated type support in JSON.
+
+.. _bug-fixes-11:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Cumulative constraint for linear solvers now accepts empty arrays.
+- show2d/show3d functions now do not add quotes around array elements
+ and work for empty arrays.
+- Add support for slicing of arrays with enumerated types.
+- Fix slicing of 1d arrays.
+- Fix bounds computation for float variable declarations.
+- When FlatZinc solver is terminated due to a timeout, do not report
+ this as an error.
+- Fix pretty-printing of multi-dimensional arrays where dimensions
+ other than the first one are empty.
+- Add support for where clauses on generator assignment expressions.
+- MiniZinc IDE: Improve dark mode by changing line numbers to dark
+ background.
+- MiniZinc IDE: Make parameter input dialog scrollable.
+- MiniZinc IDE: Fix solution compression limit, and output one solution
+ per block of compressed solutions.
+
+.. _v2.2.0:
+
+`Version 2.2.0 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 24 August 2018)
+
+This is a major release of MiniZinc, introducing many new features and
+improvements.
+
+Major new features:
+^^^^^^^^^^^^^^^^^^^
+
+- **New minizinc command line tool**
+ Previous releases contained a ``minizinc`` command line tool that was
+ not much more than a simple script that could execute the compiler,
+ solver and output processor. The ``minizinc`` executable in version
+ 2.2.0 is now the main frontend to compilation and solving and
+ integrates all of the functionality. It has access to all installed
+ MiniZinc solvers (both internal solvers and those interfaced through
+ FlatZinc files), and can automatically select the required options
+ (e.g., to include the solver-specific MiniZinc globals library).
+ You can get a list of available solvers using the ``--solvers``
+ command line option, and select a solver using ``--solver``. The
+ ``minizinc`` executable can now also be used as a replacement for
+ ``mzn2fzn`` (using ``-c``) and ``solns2out`` (using ``--ozn-file``).
+- **Multi-pass compilation**
+ The compiler can now perform multiple passes in order to improve the
+ target FlatZinc code. This can be controlled using the ``-O`` command
+ line flags (``-O0`` to ``-O4``). Multi-pass compilation is
+ particularly useful when the target solver requires sophisticated
+ decomposition of global constraints (such as for MIP solvers).
+- **Solution checking**
+ You can now supply an additional model that will be used to check
+ each solution produced by your main model. This can be useful for
+ teaching MiniZinc (to give students automatic feedback) and if your
+ main model is very complex but checking that a solution is correct is
+ easy.
+- **MIP solvers:** support for FICO Xpress, and loading IBM ILOG CPLEX
+ as a plugin
+ We have added support for FICO Xpress (this requires compiling
+ MiniZinc from sources). CPLEX can now be loaded as a plugin, which
+ means that the binary distribution of MiniZinc has built-in CPLEX
+ support (just bring your own CPLEX dll).
+- **Language extensions**
+ The MiniZinc language has been extended with two new features.
+
+ - Array slicing introduces syntax to conveniently select rows,
+ columns or entire slices of arrays. For example, ``x[3,..]``
+ selects the third row of array ``x``, while ``x[..,4]`` selects
+ the fourth column, and ``x[3..5,2..7]`` selects a slice of rows 3
+ to 5 and columns 2 to 7.
+ - Generator expressions can now contain multiple where clauses, e.g.
+ ``forall (i in S where foo(i), j in T where i < j) (bar(i,j))``
+ This enables more efficient compilation compared to evaluating all
+ where clauses in the inner-most generator. In addition to
+ iteration (``i in S``), generators can now contain assignment
+ expressions (``j=foo(i)``). This enables intermediate definitions
+ that can then be used in further generators.
+
+Changes and minor features:
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- The value of the objective can now be added automatically to the
+ output using the ``--output-objective`` command line option. Using
+ ``--output-mode dzn``, this allows automatic output of all the free
+ variables of the model.
+- Models that do not contain a solve item are now accepted and treated
+ as ``solve satisfy``
+- Support for naming constraints and expressions (using ``::"name"``
+ syntax)
+- Error messages have been improved, they now contain more accurate
+ location information.
+- The compiler can be instructed to accept multiple assignments to the
+ same parameter (as long as they are all identical), using the
+ ``--allow-multiple-assignments`` command line option.
+- Annotations for supplying warm start values have been added to the
+ standard library (currently supported by the MIP solvers Gurobi and
+ IBM ILOG CPLEX).
+- The compiler now accepts multiple .mzn files as input.
+- Memory consumption and garbage collection performance has been
+ improved.
+- The conditional expression has been extended to support
+ ``if then endif`` (where ```` is bool)
+- Decomposition of one variable type to another (e.g. set into array of
+ bool) has been improved.
+- MIP solvers Gurobi and IBM ILOG CPLEX use node files when over 3GB
+ working memory
+- Gurobi and CPLEX support the MIPfocus parameter
+- Gurobi supports MiniZinc search annotations by setting fixed
+ branching priorities
+
+.. _bug-fixes-12:
+
+Bug fixes:
+^^^^^^^^^^
+
+Consult the bug tracker at
+https://github.com/MiniZinc/libminizinc/issues
+
+.. _v2.1.7:
+
+`Version 2.1.7 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 10 January 2018)
+
+.. _changes-8:
+
+Changes:
+^^^^^^^^
+
+- Improved linearisation for some element constraints.
+- Improve performance of optimisation phase by using a queue instead of
+ a stack.
+- Add --dll option for Gurobi backend to specify the Gurobi DLL to
+ load.
+- Add more defines_var annotations.
+
+.. _bug-fixes-13:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix generation of variable names in output model (sometimes could
+ contain duplicates).
+- Fix enum type inference for array literals with empty sets as their
+ first arguments. Fixes :bugref:`180`.
+- Fix incorrect simplification of float domain constraints. Fixes :bugref:`159`.
+- Fix ceil builtin for float values.
+- Add superset decomposition for solvers that do not support set
+ variables.
+- Fix three bugs in the garbage collector.
+- Fix a bug in flattening that would create duplicate variables when a
+ variable declaration referred to another one in its type-inst.
+- Fix a crash in flattening of partial functions. Fixes :bugref:`187`.
+- Add missing deopt builtins for all par types.
+- Fix output for arrays of sets of enums.
+- Define more functions on par opt types. Fixes :bugref:`188`.
+- Fix type checker to accept arrays of opt set values.
+- Support printing of opt enum types. Fixes :bugref:`189`.
+- Fix evaluation of comprehensions in recursive functions.
+- Fix output of Gurobi backend when used in conjunction with solns2out.
+- Fix pthread linking for mzn-cbc.
+- Catch type error when set literal is declared that contains another
+ set.
+
+IDE changes and bug fixes:
+^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Fix problem where files with a . in the filename could not be run.
+- Fix font settings (were not saved reliably on some platforms).
+- Enable generic interface for submitting assignments (not just to
+ Coursera).
+- Fix output handling for solvers that do not run mzn2fzn.
+- Fix hidden solution display when there are exactly as many solutions
+ as the configured threshold for hiding solutions.
+- Add configuration option to print timing information for each
+ solution.
+
+.. _v2.1.6:
+
+`Version 2.1.6 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 22 September 2017)
+
+.. _bug-fixes-14:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fully evaluate parameters before binding formal arguments when
+ evaluating call expressions. Fixes :bugref:`177`.
+- Fix incorrect simplification of Boolean constraints assigned to
+ variables that are assigned to false.
+- Fix bug in flattening of linear equations that contain the same
+ variable on both sides.
+- Fix un-trailing for let expressions, which could sometimes cause
+ incorrect code to be emitted when lets are evaluated in nested loops.
+ Fixes :bugref:`166`.
+- Fix bug in JSON output of one-dimensional array literals.
+- Fix unification of enum type-inst variables.
+
+.. _v2.1.5:
+
+`Version 2.1.5 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 17 May 2017)
+
+.. _changes-9:
+
+Changes:
+^^^^^^^^
+
+- Some improvements to the linearisation library.
+- Make parser read multiple .mzn files correctly.
+- Enable better bounds computation for array access expressions on
+ fixed arrays.
+- Perform better constant folding during optimisation phase. Fixes :bugref:`155`.
+- Don't rewrite pow function into multiplication in the case of power
+ of 2.
+- Save some memory by making certain internal data structures more
+ compact.
+- Improve source code location of identifiers in generator calls
+ (should give more precise error messages).
+- Produce an error message when a comprehension attempts to iterate
+ over an infinite set.
+- Produce better error messages for operations on infinite values
+ (previously some errors did not contain a source code location).
+- Speed up garbage collection by pre-allocating some memory.
+
+.. _bug-fixes-15:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix range check for float literals in arrays.
+- Fix a bug where a constraint could be removed incorrectly. Fixes :bugref:`150`.
+- Include variables for dzn and json output from all included models,
+ not just the main model. Fixes :bugref:`153`.
+- Produce multi-dimensional arrays in json output. Fixes :bugref:`156` and :bugref:`157`.
+- Remove incorrect closing bracket from json output. Fixes :bugref:`154`.
+- Fix bounds computation of par int and float arrays.
+- Don't allow var access to arrays of strings or annotations (since
+ that would require an element constraint and var string / var ann
+ types).
+- Introduce int2float constraints where necessary for some
+ linearisations.
+
+.. _v2.1.4:
+
+`Version 2.1.4 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 13 March 2017)
+
+.. _changes-10:
+
+Changes:
+^^^^^^^^
+
+- Add warning for MIP solvers that do not support -a option for
+ satisfaction problems.
+- Print introduced variable names with additional underscore to make
+ debugging FlatZinc easier. Fixes :bugref:`147`.
+- Add support for pow function in linearisation library.
+- Add support for parallel solving with CBC.
+- Flatten top-level conjunctions in the order defined in the model.
+
+.. _bug-fixes-16:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix major race condition that would crash the IDE when it didn't
+ detect that a solver process had finished.
+- Improve HTML output in the IDE by making sure every line is
+ terminated by a newline.
+- Fix a garbage collection bug that could cause dangling pointers when
+ expressions were copied.
+- Fix type checker to allow empty arrays to be assigned to variables
+ declared as arrays of enums.
+- Fix infeasibility check in MIP translation for some inequality
+ constraints.
+- Improved defines_var annotations for reified xor constraints. Fixes
+ :bugref:`146`.
+- Fix output of empty integer sets and deal with empty arrays in output
+ models.
+- Fix MIP translation when boolean variables were removed due to
+ aliasing.
+- Improve corner cases for linearisation of cumulative constraint.
+- Properly report undefinedness in par bool expressions.
+- Enable some additional constant folding during flattening. Fixes :bugref:`149`.
+
+.. _v2.1.3:
+
+`Version 2.1.3 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 6 February 2017)
+
+.. _changes-11:
+
+Changes:
+^^^^^^^^
+
+- Remove more internal annotations from the generated FlatZinc.
+- Detect failure earlier if optimisation pass leads to fixing of
+ variables outside their domains.
+
+.. _bug-fixes-17:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix CBC backend to correctly print UNSAT message for models where the
+ compiler already detected unsatisfiability, and print solution
+ separators even where there is no other output.
+- Add missing var_dom function for arrays of optional integer
+ variables. Fixes :bugref:`133`.
+- Fix aliasing for optional integer variables. Fixes :bugref:`132`.
+- Remove all annotations from output model.
+- Fix computation of return type for functions that return arrays of
+ enums.
+- Don't output newline if user-defined solution separator or status
+ message is empty
+- Fix return type computation for functions where return type contains
+ enums.
+- Check finiteness of float literals and bounds. Fixes :bugref:`138`.
+- More checks for function return values. Fixes :bugref:`136`.
+- Fix var int comprehensions (now triggers error message instead of
+ crash for var set of int comprehensions). Fixes :bugref:`135`.
+- Fix output of variables with quoted identifiers.
+- Fix flattening of let expressions that contain variables with
+ undefined (i.e., partial) right hand side.
+- Make printing of error messages to stdout or stderr more consistent
+ across executables.
+- Fix type checking of initialisation of enum types.
+- Improve error messages for array access and index set errors. Fixes
+ :bugref:`131`.
+- Fix definition of multi-dimensional element constraints to impose
+ correct bounds on index variables.
+- Fix binding analysis during type checking, which did not handle the
+ shadowing of top-level declarations by comprehension generators
+ correctly. Fixes :bugref:`129`.
+
+.. _v2.1.2:
+
+`Version 2.1.2 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 20 December 2016)
+
+.. _bug-fixes-18:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug in the type checking for generators that iterate over
+ arrays of enums.
+- Fix a bug in the output handling of arrays of enums.
+- Fix handling of multiple output items (only the last item was
+ compiled, now the concatenation is used for output as defined in the
+ specification).
+
+.. _v2.1.1:
+
+`Version 2.1.1 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 14 December 2016)
+
+.. _changes-12:
+
+Changes:
+^^^^^^^^
+
+- Add missing min/max functions for set variables. Can be redefined to
+ solver builtins using the new redefinitions-2.1.1.mzn library file.
+- Add support for option type expressions as objective functions.
+- Automatically coerce arrays constructed using ++ to any enum index
+ set (in addition to array literals and comprehensions).
+
+.. _bug-fixes-19:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Include cmath header to fix compilation issues with some compilers.
+ Fixes :bugref:`125`.
+- Fix a garbage collection bug in the type checking for enumerated
+ types that would sometimes lead to crashes or incorrect error
+ messages.
+- Fix type checking of comprehensions that involve enumerated types.
+- Fix bounds computation for var sets of enumerated types.
+- Support anon_enum function as documented.
+
+.. _v2.1.0:
+
+`Version 2.1.0 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 17 November 2016)
+
+.. _changes-13:
+
+Changes:
+^^^^^^^^
+
+- MiniZinc now supports enumerated types.
+- Solvers can be interfaced directly to the MiniZinc library, and
+ MiniZinc comes with direct support for the CBC, Gurobi and CPLEX MIP
+ solvers.
+- The linearisation library has been updated, resulting in much better
+ FlatZinc being generated for MIP solvers.
+- Data files can be in JSON format, and MiniZinc can produce JSON
+ output (using the --output-mode command line option).
+- Variables can be annotated as ::add_to_output instead of writing an
+ output item.
+- The compiler can output information about the parameters and output
+ variables of a model (using the --model-interface-only option).
+- Floats are handled better (detecting infinities and handling sets of
+ floats).
+- Bounds can be computed for more expressions (instead of failing with
+ an error message).
+
+.. _bug-fixes-20:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug in optimization that could remove variables even if they
+ are used. Fixes :bugref:`123`.
+- Fix float variable declarations with sets of floats as domains. Fixes
+ :bugref:`117` and :bugref:`98`.
+- Fix type checking and evaluation of asserts with array arguments.
+ Fixes :bugref:`109`.
+- Fix abs(var float) declaration to work on floats without declared
+ bounds. Fixes :bugref:`106`.
+- Fix a bug in the computation of int and float bounds that could
+ result in incorrect bounds in some cases. Fixes :bugref:`94`.
+- Fix garbage collection when creating output models. Fixes :bugref:`77`.
+- Fix binary operators on optional variables (in some cases comparison
+ operators were reversed).
+- Fix optimization of unconstrained variables (could sometimes lead to
+ constraints being removed although they were not subsumed).
+
+.. _v2.0.14:
+
+`Version 2.0.14 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 31 July 2016)
+
+.. _changes-14:
+
+Changes:
+^^^^^^^^
+
+- Less aggressive aggregation of linear expressions in cases where it
+ leads to much less efficient FlatZinc.
+- Don't create temporary variable for an array literal if it is
+ discarded immediately anyway.
+- Only create new partiality variable for if-then-else expression if
+ there's at least one var condition.
+- Replace recursive definitions of array_intersect and array_union with
+ iterative ones.
+
+.. _bug-fixes-21:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Don't report warnings about partiality when using extended generator
+ expressions.
+- Include cmath to enable building with some versions of gcc.
+- Constrain result of function call based on function return type if
+ necessary.
+- Make sure linear expressions generated during binding of variables
+ are properly flattened (including simplification of the linear
+ expression)
+
+.. _v2.0.13:
+
+`Version 2.0.13 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 26 March 2016)
+
+.. _bug-fixes-22:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug in the Common Subexpression Elimination table of the
+ compiler, which could lead to some constraints being dropped
+ (especially when using linear redefinitions).
+- The output model sometimes did not include all required definitions,
+ in particular when array declarations used identifiers to specify the
+ dimensions.
+- The generated FlatZinc sometimes still contained bool variables that
+ were not connected to the rest of the model, which could produce
+ incorrect solutions being printed.
+- Fix a bug where warnings (e.g. about partial functions) could lead to
+ crashes.
+- Fix the bounds computation for integer and float variables, which
+ could produce incorrect bounds for linear expressions. Fixes :bugref:`94`.
+- Fix a bug in the IDE that caused solver output to be shown
+ incompletely in some cases.
+
+.. _v2.0.12:
+
+`Version 2.0.12 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 25 February 2016)
+
+.. _changes-15:
+
+Changes:
+^^^^^^^^
+
+- Partial functions are now always evaluated in their Boolean context,
+ independent of whether they are par or var. If the result of a
+ partial function is statically known to be undefined (such as
+ division by zero or array access out of bounds), and it is used in a
+ constraint expression, this now results in a warning instead of an
+ error. Warnings can be turned off using the ::maybe_partial
+ annotation. Fixes :bugref:`43` and :bugref:`74`.
+
+.. _bug-fixes-23:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug in the optimisation phase related to unification of aliased
+ variables.
+- Fix short-circuit evaluation of Boolean expressions.
+- Fix a bug in the optimisation phase related to repeated
+ simplification of some Boolean expressions.
+- Handle errors in output produced by solver without solns2out
+ crashing. Fixes :bugref:`80`.
+- Fix a bug in the integer bounds computation that caused bool2int with
+ an embedded conditional to crash.
+- Fix a problem with short-circuit compilation of == expressions when
+ one side was a var opt bool.
+- Stop compilation when model is failed. Fixes a bug where mzn2fzn
+ would sometimes not clean up the FlatZinc enough for the solver.
+
+.. _v2.0.11:
+
+`Version 2.0.11 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 15 January 2016)
+
+.. _bug-fixes-24:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix parsing of hex and octal literals. Fixes :bugref:`71`.
+- Fix compilation of extended comprehensions. Fixes :bugref:`72`.
+- Fix computation of float array access bounds.
+- Fix aggregation of clauses (could sometimes ignore the negative
+ literals).
+
+.. _v2.0.10:
+
+`Version 2.0.10 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 9 December 2015)
+
+.. _bug-fixes-25:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix a bug in the optimiser that could lead to undefined variables in
+ the generated FlatZinc. Fixes :bugref:`70`.
+
+.. _v2.0.9:
+
+`Version 2.0.9 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 6 December 2015)
+
+.. _bug-fixes-26:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Need to take return type into account when copying functions to
+ output model. Fixes :bugref:`55`.
+- Evaluate calls that result in arrays using eval_arraylit. Fixes :bugref:`57`.
+- Move inverse function to its own library file, so that it remains
+ available when a solver provides an alternative for the inverse
+ predicate.
+- Optimisation phase now recursively checks constraints when elements
+ in an array become fixed.
+- Fix CMakeLists file to work for paths that contain spaces.
+- Distinguish between infix operators and regular functions in the
+ generated html documentation. Fixes :bugref:`61`.
+- Made parser more robust against incorrect code.
+- Fix increment/decrement operators for IntVals and make all operations
+ throw correct overflow exceptions.
+- Fix automatic type coercion for variables declared in let
+ expressions.
+- Fix a crash when printing some error messages.
+- Fix compute_div_bounds builtin to return correct result for a
+ division by zero.
+- Fix optimisation of Boolean constraints to use pointer equality
+ instead of structural equality (same expression can occur multiple
+ times in the FlatZinc).
+- Only optimise constraints that have not been removed yet.
+- Fix declaration of functional version of bin_packing_load. Fixes :bugref:`64`.
+- Set type of arrays returned from polymorphic functions. Fixes :bugref:`65`.
+- Fix parsing of quoted unary operator calls.
+- Only compute set functions when bounds are valid. Fixes :bugref:`66`.
+- Compute proper bounds for if-then-else expressions.
+- Report error when no reified version of a constraint is available.
+ Fixes :bugref:`67`.
+- Fix type checking of annotations on binary operators.
+- Keep annotations when rewriting linear constraints and remove
+ is_defined_var annotations from fixed variables. Fixes :bugref:`69`.
+
+.. _changes-16:
+
+Changes:
+^^^^^^^^
+
+Integer, Boolean and float literals are now cached to achieve better
+memory performance for some models.
+
+Improve performance of parsing integer literals.
+
+Improve handling of clause constraints.
+
+Add source files of MiniZinc specification to the repository.
+
+Limit maximum array size to enable better error messages.
+
+Add implied_constraint predicate as a synonym for redundant_constraint.
+
+.. _v2.0.8:
+
+`Version 2.0.8 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 19 October 2015)
+
+.. _bug-fixes-27:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix incorrect negation of some reified comparisons.
+- Make lb/ub functions work in more cases.
+- Fix several bugs in the optimisation phase (could lead to incorrect
+ FlatZinc and crashes).
+- Fix a problem with reverse mapper functions when the result of the
+ reverse mapper can be fixed to a constant.
+
+.. _v2.0.7:
+
+`Version 2.0.7 `__
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+(released 5 October 2015)
+
+.. _changes-17:
+
+Changes:
+^^^^^^^^
+
+- Improved propagation of Boolean constants in the optimisation phase.
+ This should result in far fewer aliases and improves simplification
+ of conjunctions, disjunctions and clauses.
+- Add special case handling for integer division by 1.
+
+.. _bug-fixes-28:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix FlatZinc generator phase, need to turn all array literal
+ arguments into 1-based single dimensional arrays.
+- Fix compilation of if-then-else expressions with var conditions
+ (which didn't implement proper partiality/totality semantics). Fixes
+ :bugref:`42`.
+- Provide correct bounds for weak opt var arithmetic. Fixes :bugref:`51`.
+- Need to be able to handle unflattened annotations. Fixes :bugref:`53`.
+- Fix generation of output model (needs to ignore items that have been
+ removed previously).
+- Add missing lb(var set of int) builtin. Fixes :bugref:`47`.
+- Check that var set declarations have a finite element type. Fixes :bugref:`46`.
+- Fix translation context for binary operators on arrays.
+- Need to access IntVal::infinity as a function, otherwise depending on
+ linker etc it may become 0 in some cases. Fixes :bugref:`40`.
+- Change pretty printer to use one less digit when printing float
+ literals. This fixes :bugref:`41` (or at least
+ provides a workaround), but some double constants may still be
+ rounded incorrectly when pretty printing and reading them back in.
+ The real fix will be to output hex float literals (coming soon).
+- Distinguish between generalised comprehensions (iterating over sets)
+ and iterating over arrays. Fixes compilation of comprehensions where
+ iteration over an array is combined with var where clauses. Fixes :bugref:`45`.
+- Fix bug in creation of output model where sometimes chains of
+ variable definitions could lead to crashes.
+- Avoi creating mutually recursive definitions in some corner cases,
+ which could cause the compiler to run into infinite loops.
+- Don't copy vardecl items to output model that are already there.
+ Fixes :bugref:`44`.
+- Remove domain from array declarations in FlatZinc (avoids problems
+ with domains where holes need to be removed and when there are
+ infinities in the domains)
+- Fix flattening of equality operator between non-opt and opt vars.
+- Check that model contains a single solve and output item during type
+ checking (previously, multiple output items were not detected and
+ resulted in incorrect .ozn files).
+- Fix flattening of xor (arguments need to be in mixed context).
+- Use is_fixed in cumulative definition.
+- Fix bug where a par right hand side of a variable mentioned in the
+ output would cause a crash.
+- Fix variable dependency tracking during rewriting in the optimisation
+ phase. Could previously lead to variables being removed that are
+ still required. Fixes :bugref:`54`.
+
+.. _v2.0.6:
+
+Version 2.0.6
+~~~~~~~~~~~~~
+
+(released 2 August 2015)
+
+.. _changes-18:
+
+Changes:
+^^^^^^^^
+
+- Add parser support for hexadecimal floating point constants.
+
+.. _bug-fixes-29:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix bounds computation for some calls (abs, int_times).
+- Fix flattening of some array declarations (when right hand side is an
+ identifier).
+- Add four missing GC locks (could lead to incorrect garbage
+ collection).
+- Compact output model only after optimisation phase (could lead to
+ incorrect items being removed from output model).
+
+.. _v2.0.5:
+
+Version 2.0.5
+~~~~~~~~~~~~~
+
+(released 31 July 2015)
+
+.. _changes-19:
+
+Changes:
+^^^^^^^^
+
+- Improve the standard decomposition for the cumulative constraint.
+- Better handling of binary operators during type checking and
+ flattening, can sometimes avoid stack overflows (e.g. for large
+ conjunctions).
+- Make ++ operator left associative (avoid stack overflows in the
+ parser).
+- Add ::domain annotations to linear constraints generated from
+ multi-dimensional element constraints.
+- Greatly improved linearisation library.
+
+.. _bug-fixes-30:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix recursive function calls that contain let expressions.
+- Fix compilation of comprehensions inside parametric functions.
+- Fix a memory leak in solns2out.
+- Fix a problem in the evaluation of binary operators.
+- Fix a bug in the flattening of array literals.
+- Fix a bug that would crash the parser on certain syntax errors in let
+ expressions.
+
+.. _v2.0.4:
+
+Version 2.0.4
+~~~~~~~~~~~~~
+
+(released 1 July 2015)
+
+.. _changes-20:
+
+Changes:
+^^^^^^^^
+
+- Models can now be read from standard input (using the "-" or
+ "--input-from-stdin" command line options). Thanks to Sebastian
+ Kosch.
+- Improved handling of bool2int during FlatZinc generation.
+
+.. _bug-fixes-31:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix unification of aliased variables which could sometimes result in
+ variables being removed although had a constraining right hand side.
+- Fix evaluation of set comprehensions.
+- Fix command line flag --no-output-ozn
+- Fix performance problem when evaluating array expressions inside
+ lets.
+- Fix flattening of bool_xor redefinitions.
+- Fix partial evaluation of some array access expressions with var
+ indexes.
+- Fix definition of geost constraint.
+- User-defined functions are now copied correctly into the output model
+ if they are referenced in the output item.
+- Set comprehensions are fully evaluated.
+
+.. _v2.0.3:
+
+Version 2.0.3
+~~~~~~~~~~~~~
+
+(Internal release that did not contain some essential fixes)
+
+.. _v2.0.2:
+
+Version 2.0.2
+~~~~~~~~~~~~~
+
+(released 26 May 2015)
+
+.. _changes-21:
+
+Changes:
+^^^^^^^^
+
+- The optimiser now removes simple domain constraints from the FlatZinc
+- The compiler now checks for integer overflows in all built-in
+ operations
+- Report an error when the FlatZinc or ozn file cannot be opened for
+ writing
+- Add support for 3d array literals (e.g. [\| \|1,2|3,4|,|5,6|7,8\| \|]
+ )
+- Add show2d and show3d functions for formatting array output
+- Add row/col functions for variable arrays (fixes :bugref:`2`)
+- Introduce builtins for creating random distributions
+- Add reverse library function
+- Postpone flattening of some reified constraints
+- Slightly improved compilation of partial function calls when it can
+ be inferred at compile time that their result is undefined
+- Allow functions with empty argument lists to be declared as function
+ int: foo(); instead of just function int: foo;
+- Improve error reporting, in particular for errors in comprehensions
+- Enable expressions a..b where a and b are integer variables
+- Add redundant_constraint and symmetry_breaking_constraint builtins,
+ these can be rewritten by solver libraries to allow e.g. local search
+ solvers to ignore redundant constraints.
+- Improve flattening of predicates that simply return their arguments
+ (makes the redundant_constraint and symmetry_breaking_constraint
+ predicates work in more situations).
+- Replace command line option --only-range-domains by optional boolean
+ value so that solver libraries can set the flag directly in their
+ redefinitions file.
+- Stop flattening immediately when a model has been found to contain an
+ inconsistency.
+- Improve flattening of array access expressions, in particular for
+ nested array accesses that can be combined into a single element
+ constraint
+- Add command line option -s or --statistics to print statistics about
+ the generated FlatZinc
+- Improve bounds computation for if-then-else expressions
+- Clause arguments are compiled in positive and negative contexts
+ instead of mixed. That means that predicates that introduce free
+ variables can now be used in the positive part of a clause.
+
+.. _bug-fixes-32:
+
+Bug fixes:
+^^^^^^^^^^
+
+- Fix simplification of linear expressions, negative coefficients could
+ sometimes result in incorrect bounds
+- Fix bounds computation for unary minus operator
+- Add missing par set comparison builtins
+- Fix bounds computation for extended comprehension syntax
+- Fix a bug in the garbage collector that could sometimes lead to
+ premature deletion of expressions
+- Fix bounds computation for set difference
+- Fix duplication of some arrays in the FlatZinc (fixes :bugref:`3`)
+- Fix bounds inference for variables bound to empty sets (fixes :bugref:`3`)
+- Fix bug in error reporting function, which would sometimes not report
+ the entire call stack
+- Fix the generation of fresh variable names for generator expressions
+- Fix subtype check to allow empty arrays as subtype of arrays of sets
+- Fix crash when using assert/2
+- Fix bug when function used in output referred to par variable
+- Fix bug in type checker, the detection of cyclic definitions was not
+ correct and could lead to stack overflows
+- Fix parser to accept expressions with two consecutive array accesses
+ (like x[3][4], which are valid MiniZinc if x is an array of sets)
+- Fix error reporting when an evaluation error occurs within a
+ comprehension generator
+- Report type error on some ambiguous function calls
+- Report type error on var sets with element type other than int
+- Report type error when trying to coerce a var set into an array
+- Report error when calling function with a value that is outside the
+ declared parameter bounds
+- Fix arg_sort builtin to implement the correct semantics
+- Fix sort_by builtin to sort in non-decreasing order, and work with
+ floats
+- Fix bug in type checker, now automatic coercions in functions defined
+ with type variables (like the comparison operators) work correctly
+- Check that index sets match for arrays assigned in let expressions
+- Fix bug in bounds inference for integer expressions with annotations
+- Fix propagation of defines_var annotation to be pushed through calls
+- Fix parser to accept empty 2d and 3d array literals
+- Fix flattening to remove defines_var annotations with par argument,
+ e.g. defines_var(2), which could be introduced by the optimisation
+ pass
+- Fix output model creation for variables that have been redefined, and
+ remove more unused variables from the FlatZinc.
+- Fix bug in the garbage collector that could result in function items
+ not being kept alive in rare cases.
+
+.. _v2.0.1:
+
+Version 2.0.1
+~~~~~~~~~~~~~
+
+(released 15 December 2014)
+
+Major bugs and changes:
+^^^^^^^^^^^^^^^^^^^^^^^
+
+- Fix optimisation phase, which was previously incorrectly removing
+ variables
+- Add support for trigonometric functions (built-ins were missing in
+ 2.0.0) and pow (var versions were missing)
+- Fix equality operator on par arrays
+- All expressions in output model are now made par
+- Improve bounds computation for float variables
+- Fix translation of functions that need automatic coercion of their
+ return value
+- Fix the array_lb and array_ub builtins, which would return incorrect
+ bounds in some cases
+
+Minor bugs and changes:
+^^^^^^^^^^^^^^^^^^^^^^^
+
+- Add space between "array" and "[" in the pretty printer, to be
+ compatible with 1.6 output
+- Output all par declarations before the var declarations in FlatZinc
+- Fix parser, which could sometimes crash on invalid input
+- Improve efficiency of bounds computation on some float expressions
+- Add special case handling for division by 1
+- Add missing float_times definition to the flatzinc builtins
+- Use correct version of var_dom for float variables
+- Output information about which files are included in verbose mode
+- Only compute bounds for "then" expressions if the "if" is not fixed
+ to false
+
+.. _v2.0.0:
+
+Version 2.0.0
+~~~~~~~~~~~~~
+
+(released 9 December 2014)
+
+MiniZinc 2.0 contains many new features and is based on a complete
+rewrite of the MiniZinc-to-FlatZinc compiler. If you are currently using
+the previous version 1.6, the new tools can be used as drop-in
+replacements. The generated FlatZinc is compatible with version 1.6, so
+all FlatZinc solvers should work without changes.
+
+MiniZinc language changes
+^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- MiniZinc now supports user-defined functions. Details have been
+ published in the paper "MiniZinc with Functions". Both functions and
+ predicates can be recursive.
+- MiniZinc now supports option types. Details have been published in
+ the paper "Modelling with Option Types in MiniZinc".
+- Let expressions have been generalised. They can now contain
+ constraint items in addition to variable declarations.
+- Array index sets can be declared using arbitrary set expressions as
+ long as they evaluate to contiguous ranges.
+- The if-then-else expression has been generalised to allow the
+ condition to be a var bool expression (instead of only par bool).
+- Array and set comprehensions as well as generator calls can now
+ iterate over variables and use var bool where conditions.
+- Any bool expression can now automatically coerce to an int
+ expression, likewise for int and float. This means that you don't
+ have to write bool2int or int2float in you models any more.
+- Equality constraints can now be posted between array expressions.
+- Arbitrary expressions can now be included ("interpolated") into
+ strings, using the syntax "some text \\(e) some more text", where e
+ is any expression. It is the same as writing "some text "++show(e)++"
+ some more text".
+
+New built-in functions
+^^^^^^^^^^^^^^^^^^^^^^
+
+- Array functions: array1d, arrayXd, row, col, has_index, has_element,
+ sort_by, sort, arg_sort, arg_min, arg_max
+
+New global constraints
+^^^^^^^^^^^^^^^^^^^^^^
+
+- arg_max, arg_min
+- arg_sort
+- k-dimensional diffn
+- disjunctive
+- geost
+- knapsack
+- network_flow
+- regular with NFAs
+- symmetric all different
+- optional scheduling constraints: alternative, span, disjunctive,
+ cumulative
+- functional versions of many global constraints
+
+New tool chain
+^^^^^^^^^^^^^^
+
+- There are a few new builtins that solvers can reimplement, these are
+ listed in the redefinitions-2.0 file.
+- Include items use a different method for finding included files.
+ Paths are now interpreted as relative to the file that has the
+ include item. That way, the mzn2fzn compiler can be called from a
+ different working directory.
+- A new tool, mzn2doc, can produce html output from the documentation
+ comments. The MiniZinc distribution contains the documentation for
+ global constraints and builtins generated directly from the library
+ source code.
diff --git a/software/minizinc/cmake/modules/FindCPlex.cmake b/software/minizinc/cmake/modules/FindCPlex.cmake
new file mode 100644
index 0000000..a626924
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindCPlex.cmake
@@ -0,0 +1,74 @@
+# - Try to find CPLEX
+# Once done this will define
+# CPLEX_FOUND - System has CPLEX
+# CPLEX_INCLUDE_DIRS - The CPLEX include directories
+# CPLEX_LIBRARIES - The libraries needed to use CPLEX
+# CPLEX_COMPILE_FLAGS - The definitions required to compile with CPLEX
+# User can set CPlex_ROOT to the preferred installation prefix
+
+set(CPLEX_COMPILE_FLAGS "-fPIC -fno-strict-aliasing -fexceptions")
+
+set(CPLEX_VERSIONS 1210 129 128 1271 127 1263 1262 1261 126)
+
+foreach(VERSION ${CPLEX_VERSIONS})
+ list(APPEND CPLEX_DEFAULT_LOC "/opt/ibm/ILOG/CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "/opt/IBM/ILOG/CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "C:\\Program Files\\IBM\\ILOG\\CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "C:\\Program Files (x86)\\IBM\\ILOG\\CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "$ENV{HOME}/Applications/IBM/ILOG/CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "/Applications/IBM/ILOG/CPLEX_Studio${VERSION}")
+ list(APPEND CPLEX_DEFAULT_LOC "/Applications/CPLEX_Studio${VERSION}")
+
+ list(APPEND CPLEX_LIB_NAMES cplex${VERSION})
+endforeach(VERSION)
+
+find_path(CPLEX_INCLUDE ilcplex/cplex.h
+ HINTS ${CPLEX_DEFAULT_LOC}
+ PATH_SUFFIXES include cplex/include)
+
+if(NOT "${CPLEX_INCLUDE}" STREQUAL "CPLEX_INCLUDE-NOTFOUND")
+ file(READ "${CPLEX_INCLUDE}/ilcplex/cplex.h" CPLEX_CONFIG)
+ string(REGEX MATCH " +\\* +Version +([0-9]+\\.[0-9]+\\.[0-9]+)" _ "${CPLEX_CONFIG}")
+ set(CPLEX_VERSION "${CMAKE_MATCH_1}")
+ unset(CPLEX_CONFIG)
+endif()
+
+if(CPLEX_PLUGIN)
+ include(CheckIncludeFiles)
+ # TODO: Cleanup this mess
+ check_include_files(dlfcn.h HAS_DLFCN_H)
+ check_include_files(Windows.h HAS_WINDOWS_H)
+ if(HAS_DLFCN_H)
+ find_library(CPLEX_LIBRARY dl)
+ elseif(HAS_WINDOWS_H)
+ set(CPLEX_LIBRARY ${CPLEX_INCLUDE})
+ endif()
+else()
+ foreach(CPLEX_LIB ${CPLEX_LIB_NAMES})
+ find_library(CPLEX_LIBRARY NAMES cplex ${CPLEX_LIB}
+ HINTS ${CPLEX_DEFAULT_LOC}
+ PATH_SUFFIXES lib/x86-64_linux/static_pic lib/x86-64_osx/static_pic lib/x64_windows_vs2013/stat_mda cplex/lib/x86-64_linux/static_pic cplex/lib/x86-64_osx/static_pic cplex/lib/x64_windows_vs2013/stat_mda)
+ if(NOT "${CPLEX_LIBRARY}" STREQUAL "CPLEX_LIBRARY-NOTFOUND")
+ break()
+ endif()
+ endforeach(CPLEX_LIB)
+endif()
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set CBC_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(CPlex
+ FOUND_VAR CPLEX_FOUND
+ REQUIRED_VARS CPLEX_INCLUDE CPLEX_LIBRARY
+ VERSION_VAR CPLEX_VERSION
+ FAIL_MESSAGE "Could NOT find CPlex, use CPlex_ROOT to hint its location"
+)
+
+if(CPLEX_PLUGIN AND HAS_WINDOWS_H AND NOT HAS_DLFCN_H)
+ unset(CPLEX_LIBRARY)
+endif()
+
+mark_as_advanced(CPLEX_INCLUDE CPLEX_LIBRARY)
+
+set(CPLEX_LIBRARIES ${CPLEX_LIBRARY})
+set(CPLEX_INCLUDE_DIRS ${CPLEX_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindGeas.cmake b/software/minizinc/cmake/modules/FindGeas.cmake
new file mode 100644
index 0000000..13eba2b
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindGeas.cmake
@@ -0,0 +1,38 @@
+# - Try to find Geas
+# Once done this will define
+# GEAS_FOUND - System has Geas
+# GEAS_INCLUDE_DIRS - The Geas include directories
+# GEAS_LIBRARIES - The libraries needed to use Geas
+# User can set Geas_ROOT to the preferred installation prefix
+# Imported target Geas will be created for linking purposes
+find_path(
+ GEAS_INCLUDE geas/c/geas.h
+ PATH_SUFFIXES include
+)
+
+find_library(
+ GEAS_LIBRARY NAMES geas libgeas
+ PATH_SUFFIXES lib
+)
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set GEAS_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(Geas
+ FOUND_VAR GEAS_FOUND
+ REQUIRED_VARS GEAS_INCLUDE GEAS_LIBRARY
+ FAIL_MESSAGE "Could NOT find Geas, use Geas_ROOT to hint its location"
+)
+
+mark_as_advanced(GEAS_INCLUDE GEAS_LIBRARY)
+
+if(GEAS_FOUND)
+ add_library(Geas UNKNOWN IMPORTED)
+ set_target_properties(Geas PROPERTIES
+ IMPORTED_LOCATION ${GEAS_LIBRARY}
+ INTERFACE_INCLUDE_DIRECTORIES ${GEAS_INCLUDE}
+ )
+endif()
+
+set(GEAS_LIBRARIES ${GEAS_LIBRARY})
+set(GEAS_INCLUDE_DIRS ${GEAS_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindGecode.cmake b/software/minizinc/cmake/modules/FindGecode.cmake
new file mode 100644
index 0000000..24a0931
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindGecode.cmake
@@ -0,0 +1,83 @@
+# - Try to find Gecode
+# Once done this will define
+# GECODE_FOUND - System has Gecode
+# GECODE_INCLUDE_DIRS - The Gecode include directories
+# GECODE_LIBRARIES - The libraries needed to use Gecode
+# GECODE_TARGETS - The names of imported targets created for gecode
+# User can set Gecode_ROOT to the preferred installation prefix
+
+find_path(GECODE_INCLUDE gecode/kernel.hh
+ PATH_SUFFIXES include)
+
+find_file(GECODE_CONFIG_LOC gecode/support/config.hpp
+ HINTS ${GECODE_INCLUDE}
+ PATH_SUFFIXES include)
+
+if(NOT "${GECODE_CONFIG_LOC}" STREQUAL "GECODE_CONFIG_LOC-NOTFOUND")
+ file(READ "${GECODE_CONFIG_LOC}" GECODE_CONFIG)
+ string(REGEX MATCH "\#define GECODE_VERSION \"([0-9]+.[0-9]+.[0-9]+)\"" _ "${GECODE_CONFIG}")
+ set(GECODE_VERSION "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define GECODE_LIBRARY_VERSION \"([0-9]+-[0-9]+-[0-9]+)\"" _ "${GECODE_CONFIG}")
+ set(GECODE_LIBRARY_VERSION "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define GECODE_STATIC_LIBS ([0-9]+)" _ "${GECODE_CONFIG}")
+ set(GECODE_STATIC_LIBS "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define GECODE_HAS_GIST" GECODE_HAS_GIST "${GECODE_CONFIG}")
+ string(REGEX MATCH "\#define GECODE_HAS_MPFR" GECODE_HAS_MPFR "${GECODE_CONFIG}")
+ unset(GECODE_CONFIG)
+endif()
+unset(GECODE_CONFIG_LOC)
+
+set(GECODE_COMPONENTS Driver Flatzinc Float Int Kernel Minimodel Search Set Support)
+if(GECODE_HAS_GIST)
+ list(APPEND GECODE_COMPONENTS Gist)
+endif()
+
+foreach(GECODE_COMP ${GECODE_COMPONENTS})
+ # Try to find gecode library
+ string(TOLOWER "gecode${GECODE_COMP}" GECODE_LIB)
+ set(GECODE_LIB_LOC "GECODE_LIB_LOC-NOTFOUND")
+ find_library(GECODE_LIB_LOC NAMES ${GECODE_LIB} lib${GECODE_LIB} ${GECODE_LIB}-${GECODE_LIBRARY_VERSION}-r-x64 ${GECODE_LIB}-${GECODE_LIBRARY_VERSION}-d-x64
+ HINTS ${GECODE_INCLUDE}
+ PATH_SUFFIXES lib)
+ if(NOT "${GECODE_LIB_LOC}" STREQUAL "GECODE_LIB_LOC-NOTFOUND")
+ list(APPEND GECODE_LIBRARY ${GECODE_LIB_LOC})
+ add_library(Gecode::${GECODE_COMP} UNKNOWN IMPORTED)
+ set_target_properties(Gecode::${GECODE_COMP} PROPERTIES
+ IMPORTED_LOCATION ${GECODE_LIB_LOC}
+ INTERFACE_INCLUDE_DIRECTORIES ${GECODE_INCLUDE})
+ set(Gecode_FIND_REQUIRED_${GECODE_COMP} TRUE)
+ set(Gecode_${GECODE_COMP}_FOUND TRUE)
+ endif()
+endforeach(GECODE_COMP)
+
+if(WIN32 AND GECODE_HAS_GIST AND GECODE_STATIC_LIBS)
+ find_package(Qt5 QUIET COMPONENTS Core Gui Widgets PrintSupport)
+ set_target_properties(Gecode::Gist PROPERTIES
+ INTERFACE_LINK_LIBRARIES "Qt5::Core;Qt5::Gui;Qt5::Widgets;Qt5::PrintSupport")
+endif()
+
+unset(GECODE_REQ_LIBS)
+unset(GECODE_LIB_WIN)
+unset(GECODE_LIB_LOC)
+
+if(GECODE_LIBRARY AND GECODE_HAS_MPFR)
+ find_package(MPFR)
+ list(APPEND GECODE_LIBRARY ${MPFR_LIBRARIES})
+ list(APPEND GECODE_TARGETS ${MPFR_LIBRARIES})
+endif()
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set GECODE_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(
+ Gecode
+ REQUIRED_VARS GECODE_INCLUDE GECODE_LIBRARY
+ VERSION_VAR GECODE_VERSION
+ HANDLE_COMPONENTS
+ FAIL_MESSAGE "Could NOT find Gecode, use Gecode_ROOT to hint its location"
+)
+
+mark_as_advanced(GECODE_INCLUDE GECODE_LIBRARY)
+
+set(GECODE_LIBRARIES ${GECODE_LIBRARY})
+set(GECODE_INCLUDE_DIRS ${GECODE_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindGurobi.cmake b/software/minizinc/cmake/modules/FindGurobi.cmake
new file mode 100644
index 0000000..a308bcc
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindGurobi.cmake
@@ -0,0 +1,82 @@
+# - Try to find Gurobi
+# Once done this will define
+# GUROBI_FOUND - System has GUROBI
+# GUROBI_INCLUDE_DIRS - The GUROBI include directories
+# GUROBI_LIBRARIES - The libraries needed to use GUROBI
+# GUROBI_COMPILE_FLAGS - The definitions required to compile with GUROBI
+# User can set Gurobi_ROOT to the preferred installation prefix
+
+option(GUROBI_PLUGIN "Build Gurobi binding as a plugin" ON)
+
+set(GUROBI_COMPILE_FLAGS "-fPIC -fno-strict-aliasing -fexceptions")
+
+set(GUROBI_VERSIONS 913 912 911 910 903 902 901 900 811 810 801 752 702)
+
+foreach(VERSION ${GUROBI_VERSIONS})
+ list(APPEND GUROBI_DEFAULT_LOC "/opt/gurobi${VERSION}/linux64")
+ list(APPEND GUROBI_DEFAULT_LOC "/opt/gurobi${VERSION}/linux64")
+ list(APPEND GUROBI_DEFAULT_LOC "C:\\gurobi${VERSION}\\win64")
+ list(APPEND GUROBI_DEFAULT_LOC "C:\\gurobi${VERSION}\\win32")
+ list(APPEND GUROBI_DEFAULT_LOC "/Library/gurobi${VERSION}/mac64")
+
+ string(SUBSTRING ${VERSION} 0 2 VERSION)
+ list(APPEND GUROBI_LIB_NAMES gurobi${VERSION})
+endforeach(VERSION)
+
+find_path(GUROBI_INCLUDE gurobi_c.h
+ PATHS $ENV{GUROBI_HOME}
+ HINTS ${GUROBI_DEFAULT_LOC}
+ PATH_SUFFIXES include)
+
+if(NOT "${GUROBI_INCLUDE}" STREQUAL "GUROBI_INCLUDE-NOTFOUND")
+ file(READ "${GUROBI_INCLUDE}/gurobi_c.h" GUROBI_CONFIG)
+ string(REGEX MATCH "\#define GRB_VERSION_MAJOR +([0-9]+)" _ "${GUROBI_CONFIG}")
+ set(GRB_VERSION_MAJOR "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define GRB_VERSION_MINOR +([0-9]+)" _ "${GUROBI_CONFIG}")
+ set(GRB_VERSION_MINOR "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define GRB_VERSION_TECHNICAL +([0-9]+)" _ "${GUROBI_CONFIG}")
+ set(GRB_VERSION_TECHNICAL "${CMAKE_MATCH_1}")
+ set(GUROBI_VERSION "${GRB_VERSION_MAJOR}.${GRB_VERSION_MINOR}.${GRB_VERSION_TECHNICAL}")
+ unset(GUROBI_CONFIG)
+endif()
+
+if(GUROBI_PLUGIN)
+ include(CheckIncludeFiles)
+ # TODO: Cleanup this mess
+ check_include_files(dlfcn.h HAS_DLFCN_H)
+ check_include_files(Windows.h HAS_WINDOWS_H)
+ if(HAS_DLFCN_H)
+ find_library(GUROBI_LIBRARY dl)
+ elseif(HAS_WINDOWS_H)
+ set(GUROBI_LIBRARY ${GUROBI_INCLUDE})
+ endif()
+else()
+ foreach(GUROBI_LIB ${GUROBI_LIB_NAMES})
+ find_library(GUROBI_LIBRARY NAMES ${GUROBI_LIB}
+ HINTS $ENV{GUROBI_HOME}
+ PATHS ${GUROBI_DEFAULT_LOC}
+ PATH_SUFFIXES lib)
+ if(NOT "${GUROBI_LIBRARY}" STREQUAL "GUROBI_LIBRARY-NOTFOUND")
+ break()
+ endif()
+ endforeach(GUROBI_LIB)
+endif()
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set GUROBI_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(Gurobi
+ FOUND_VAR GUROBI_FOUND
+ REQUIRED_VARS GUROBI_INCLUDE GUROBI_LIBRARY
+ VERSION_VAR GUROBI_VERSION
+ FAIL_MESSAGE "Could NOT find Gurobi, use Gurobi_ROOT to hint its location"
+)
+
+if(GUROBI_PLUGIN AND HAS_WINDOWS_H AND NOT HAS_DLFCN_H)
+ unset(GUROBI_LIBRARY)
+endif()
+
+mark_as_advanced(GUROBI_INCLUDE GUROBI_LIBRARY)
+
+set(GUROBI_LIBRARIES ${GUROBI_LIBRARY})
+set(GUROBI_INCLUDE_DIRS ${GUROBI_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindMPFR.cmake b/software/minizinc/cmake/modules/FindMPFR.cmake
new file mode 100644
index 0000000..c61665d
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindMPFR.cmake
@@ -0,0 +1,25 @@
+### Try to find MPFR
+# Once done this will define
+# MPFR_FOUND - System has MPFR
+# MPFR_INCLUDE_DIRS - The MPFR include directories
+# MPFR_LIBRARIES - The libraries needed to use MPFR
+
+find_path(MPFR_INCLUDE NAMES mpfr.h
+ PATHS $ENV{GMPDIR} $ENV{MPFRDIR} ${INCLUDE_INSTALL_DIR})
+
+find_library(MPFR_LIBRARY mpfr
+ PATHS $ENV{GMPDIR} $ENV{MPFRDIR} ${LIB_INSTALL_DIR})
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set MPFR_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(MPFR
+ FOUND_VAR MPFR_FOUND
+ REQUIRED_VARS MPFR_LIBRARY MPFR_INCLUDE
+ FAIL_MESSAGE "Could NOT find MPFR, use MPFR_ROOT to hint its location"
+)
+
+mark_as_advanced(MPFR_INCLUDE MPFR_LIBRARY)
+
+set(MPFR_INCLUDES ${MPFR_INCLUDE})
+set(MPFR_LIBRARIES ${MPFR_LIBRARY})
diff --git a/software/minizinc/cmake/modules/FindOsiCBC.cmake b/software/minizinc/cmake/modules/FindOsiCBC.cmake
new file mode 100644
index 0000000..427bb75
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindOsiCBC.cmake
@@ -0,0 +1,91 @@
+# - Try to find CBC
+# Once done this will define
+# OSICBC_FOUND - System has CBC
+# OSICBC_INCLUDE_DIRS - The CBC include directories
+# OSICBC_LIBRARIES - The libraries needed to use CBC
+# GOSICBC_TARGETS - The names of imported targets created for CBC
+# User can set OsiCBC_ROOT to the preferred installation prefix
+
+set(OSICBC_FIND_FILES coin/CbcSolver.hpp coin/CglPreProcess.hpp coin/ClpConfig.h coin/CoinSignal.hpp coin/OsiClpSolverInterface.hpp coin/OsiSolverInterface.hpp)
+
+foreach(OSICBC_FILE ${OSICBC_FIND_FILES})
+ set(OSICBC_FILE_LOC "OSICBC_LIB_LOC-NOTFOUND")
+ find_path(OSICBC_FILE_LOC ${OSICBC_FILE}
+ PATH_SUFFIXES cbc cgl clp coinutils osi include)
+ if("${OSICBC_FILE_LOC}" STREQUAL "OSICBC_FILE_LOC-NOTFOUND")
+# message(STATUS "OsiCBC: Could not find file `${OSICBC_FILE}`")
+ set(OSICBC_INCLUDE "")
+ break()
+ endif()
+ list(APPEND OSICBC_INCLUDE ${OSICBC_FILE_LOC})
+ # Add "/coin" for CBC internal dependencies
+ list(APPEND OSICBC_INCLUDE ${OSICBC_FILE_LOC}/coin)
+endforeach(OSICBC_FILE)
+
+list(REMOVE_DUPLICATES OSICBC_INCLUDE)
+unset(OSICBC_FIND_FILES)
+unset(OSICBC_FILE_LOC)
+
+find_file(CBC_CONFIG_LOC NAMES coin/config_cbc_default.h coin/CbcConfig.h
+ HINTS ${OSICBC_INCLUDE}
+ PATH_SUFFIXES cbc)
+
+if(NOT "${CBC_CONFIG_LOC}" STREQUAL "CBC_CONFIG_LOC-NOTFOUND")
+ file(READ "${CBC_CONFIG_LOC}" CBC_CONFIG)
+ string(REGEX MATCH "\#define +CBC_VERSION +\"([0-9]+.[0-9]+)\"" _ "${CBC_CONFIG}")
+ set(OSICBC_VERSION "${CMAKE_MATCH_1}")
+ unset(CBC_CONFIG)
+endif()
+unset(CBC_CONFIG_LOC)
+
+if(WIN32 AND NOT UNIX)
+ set(OSICBC_REQ_LIBS Osi OsiClp OsiCbc Clp Cgl Cbc CbcSolver CoinUtils)
+else()
+ set(OSICBC_REQ_LIBS CbcSolver Cbc Cgl OsiClp Clp Osi CoinUtils)
+endif()
+
+foreach(OSICBC_LIB ${OSICBC_REQ_LIBS})
+ set(OSICBC_LIB_LOC "OSICBC_LIB_LOC-NOTFOUND")
+ find_library(OSICBC_LIB_LOC NAMES ${OSICBC_LIB} lib${OSICBC_LIB}
+ PATH_SUFFIXES lib)
+ if("${OSICBC_LIB_LOC}" STREQUAL "OSICBC_LIB_LOC-NOTFOUND")
+# message(STATUS "OsiCBC: Could not find library `${OSICBC_LIB}`")
+ set(OSICBC_LIBRARY "")
+ break()
+ endif()
+ list(APPEND OSICBC_LIBRARY ${OSICBC_LIB_LOC})
+ add_library(${OSICBC_LIB} UNKNOWN IMPORTED)
+ set_target_properties(${OSICBC_LIB} PROPERTIES
+ IMPORTED_LOCATION ${OSICBC_LIB_LOC}
+ INTERFACE_INCLUDE_DIRECTORIES "${OSICBC_INCLUDE}")
+ list(APPEND OSICBC_TARGETS ${OSICBC_LIB})
+endforeach(OSICBC_LIB)
+
+unset(OSICBC_REQ_LIBS)
+unset(OSICBC_LIB_LOC)
+
+if(UNIX AND NOT WIN32 AND NOT DEFINED EMSCRIPTEN)
+ find_package(ZLIB)
+ if(NOT ZLIB_FOUND)
+ message(STATUS "OsiCBC: Missing dependency `Zlib`")
+ set(OSICBC_LIBRARY "")
+ else()
+ list(APPEND OSICBC_LIBRARY ${ZLIB_LIBRARIES})
+ list(APPEND OSICBC_TARGETS ${ZLIB_LIBRARIES})
+ endif()
+endif()
+
+include(FindPackageHandleStandardArgs)
+# handle the QUIETLY and REQUIRED arguments and set CBC_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(OsiCBC
+ FOUND_VAR OSICBC_FOUND
+ REQUIRED_VARS OSICBC_INCLUDE OSICBC_LIBRARY
+ VERSION_VAR OSICBC_VERSION
+ FAIL_MESSAGE "Could NOT find OsiCBC, use OsiCBC_ROOT to hint its location"
+)
+
+mark_as_advanced(OSICBC_INCLUDE OSICBC_LIBRARY)
+
+set(OSICBC_LIBRARIES ${OSICBC_LIBRARY})
+set(OSICBC_INCLUDE_DIRS ${OSICBC_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindSCIP.cmake b/software/minizinc/cmake/modules/FindSCIP.cmake
new file mode 100644
index 0000000..5d2a06e
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindSCIP.cmake
@@ -0,0 +1,39 @@
+# - Try to find SCIP
+# Once done this will define
+# SCIP_FOUND - System has SCIP
+# SCIP_INCLUDE_DIRS - The SCIP include directories
+# User can set SCIP_ROOT to the preferred installation prefix
+
+# We only need headers, since we always compile SCIP as a plugin
+find_path(SCIP_INCLUDE scip/scip.h
+ PATH_SUFFIXES include)
+
+find_file(SCIP_CONFIG_LOC scip/config.h
+ HINTS ${SCIP_INCLUDE}
+ PATH_SUFFIXES include)
+
+if(NOT "${SCIP_CONFIG_LOC}" STREQUAL "SCIP_CONFIG_LOC-NOTFOUND")
+ file(READ "${SCIP_CONFIG_LOC}" SCIP_CONFIG)
+ string(REGEX MATCH "\#define SCIP_VERSION_MAJOR +([0-9]+)" _ "${SCIP_CONFIG}")
+ set(SCIP_VERSION_MAJOR "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define SCIP_VERSION_MINOR +([0-9]+)" _ "${SCIP_CONFIG}")
+ set(SCIP_VERSION_MINOR "${CMAKE_MATCH_1}")
+ string(REGEX MATCH "\#define SCIP_VERSION_PATCH +([0-9]+)" _ "${SCIP_CONFIG}")
+ set(SCIP_VERSION_PATCH "${CMAKE_MATCH_1}")
+ set(SCIP_VERSION "${SCIP_VERSION_MAJOR}.${SCIP_VERSION_MINOR}.${SCIP_VERSION_PATCH}")
+ unset(SCIP_CONFIG)
+endif()
+unset(SCIP_CONFIG_LOC)
+
+# handle the QUIETLY and REQUIRED arguments and set SCIP_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(SCIP
+ FOUND_VAR SCIP_FOUND
+ REQUIRED_VARS SCIP_INCLUDE
+ VERSION_VAR SCIP_VERSION
+ FAIL_MESSAGE "Could NOT find SCIP, use SCIP_ROOT to hint its location"
+)
+
+mark_as_advanced(SCIP_INCLUDE SCIP_CONFIG_LOC)
+
+set(SCIP_INCLUDE_DIRS ${SCIP_INCLUDE})
diff --git a/software/minizinc/cmake/modules/FindXpress.cmake b/software/minizinc/cmake/modules/FindXpress.cmake
new file mode 100644
index 0000000..04c1761
--- /dev/null
+++ b/software/minizinc/cmake/modules/FindXpress.cmake
@@ -0,0 +1,23 @@
+# - Try to find FICO Xpress
+# Once done this will define
+# XPRESS_FOUND - System has FICO Xpress
+# XPRESS_INCLUDE_DIRS - The FICO Xpress include directories
+# User can set Xpress_ROOT to the preferred installation prefix
+
+#TODO: Check default installation locations
+find_path(XPRESS_INCLUDE xprs.h
+ PATHS $ENV{XPRESSDIR} $ENV{XPRESS} $ENV{XPRESS_DIR}
+ HINTS /opt/xpressmp C:/xpressmp /Applications/FICO\ Xpress/xpressmp
+ PATH_SUFFIXES include)
+
+# handle the QUIETLY and REQUIRED arguments and set XPRESS_FOUND to TRUE
+# if all listed variables are TRUE
+find_package_handle_standard_args(Xpress
+ FOUND_VAR XPRESS_FOUND
+ REQUIRED_VARS XPRESS_INCLUDE
+ FAIL_MESSAGE "Could NOT find Xpress, use Xpress_ROOT to hint its location"
+)
+
+mark_as_advanced(XPRESS_INCLUDE)
+
+set(XPRESS_INCLUDE_DIRS ${XPRESS_INCLUDE})
diff --git a/software/minizinc/cmake/scripts/md5_gen.cmake b/software/minizinc/cmake/scripts/md5_gen.cmake
new file mode 100644
index 0000000..2075453
--- /dev/null
+++ b/software/minizinc/cmake/scripts/md5_gen.cmake
@@ -0,0 +1,45 @@
+# Script to update the cached lexer and parser
+# Run after modifying lexer.lxx and/or parser.yxx
+#
+# 1. generate lexer and parser by building libminizinc
+# 2. run cmake -DPROJECT_SOURCE_DIR=. -DPROJECT_BINARY_DIR=build -P cmake/scripts/md5_gen.cmake
+# replacing . and build with the source and binary directory
+# add -DFORCE=ON to force the renewing of generated files when md5's still match.
+
+option(FORCE "Force the renewing of generated files" OFF)
+
+macro(MD5 filename md5sum)
+ file(READ "${filename}" RAW_MD5_FILE)
+ string(REGEX REPLACE "\r" "" STRIPPED_MD5_FILE "${RAW_MD5_FILE}")
+ string(MD5 ${md5sum} "${STRIPPED_MD5_FILE}")
+endmacro(MD5)
+
+# When updating the cached files, update MD5 sums defined in this file
+include(${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake)
+
+MD5("${PROJECT_SOURCE_DIR}/lib/lexer.lxx" lexer_lxx_md5)
+MD5("${PROJECT_SOURCE_DIR}/lib/parser.yxx" parser_yxx_md5)
+MD5("${PROJECT_SOURCE_DIR}/lib/support/regex/lexer.lxx" regex_lexer_lxx_md5)
+MD5("${PROJECT_SOURCE_DIR}/lib/support/regex/parser.yxx" regex_parser_yxx_md5)
+
+
+if(FORCE OR (NOT "${lexer_lxx_md5}" STREQUAL "${lexer_lxx_md5_cached}"))
+ file(COPY "${PROJECT_BINARY_DIR}/lexer.yy.cpp" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached")
+endif()
+if(FORCE OR (NOT "${parser_yxx_md5}" STREQUAL "${parser_yxx_md5_cached}"))
+ file(COPY "${PROJECT_BINARY_DIR}/parser.tab.cpp" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached")
+ file(COPY "${PROJECT_BINARY_DIR}/include/minizinc/parser.tab.hh" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached/minizinc")
+endif()
+if(FORCE OR (NOT "${regex_lexer_lxx_md5}" STREQUAL "${regex_lexer_lxx_md5_cached}"))
+ file(COPY "${PROJECT_BINARY_DIR}/regex_lexer.yy.cpp" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached")
+endif()
+if(FORCE OR (NOT "${regex_parser_yxx_md5}" STREQUAL "${regex_parser_yxx_md5_cached}"))
+ file(COPY "${PROJECT_BINARY_DIR}/regex_parser.tab.cpp" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached")
+ file(COPY "${PROJECT_BINARY_DIR}/include/minizinc/support/regex_parser.tab.hh" DESTINATION "${PROJECT_SOURCE_DIR}/lib/cached/minizinc/support")
+endif()
+
+set(MD5_TEMPLATE "set(lexer_lxx_md5_cached \"${lexer_lxx_md5}\")")
+set(MD5_TEMPLATE "${MD5_TEMPLATE}\nset(parser_yxx_md5_cached \"${parser_yxx_md5}\")")
+set(MD5_TEMPLATE "${MD5_TEMPLATE}\nset(regex_lexer_lxx_md5_cached \"${regex_lexer_lxx_md5}\")")
+set(MD5_TEMPLATE "${MD5_TEMPLATE}\nset(regex_parser_yxx_md5_cached \"${regex_parser_yxx_md5}\")")
+file(WRITE "${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake" ${MD5_TEMPLATE})
diff --git a/software/minizinc/cmake/support/ccache_setup.cmake b/software/minizinc/cmake/support/ccache_setup.cmake
new file mode 100644
index 0000000..fac062a
--- /dev/null
+++ b/software/minizinc/cmake/support/ccache_setup.cmake
@@ -0,0 +1,25 @@
+option(USE_CCACHE "Use ccache to speed up compilation when found on the system" TRUE)
+
+find_program(CCACHE_PROGRAM ccache)
+if(USE_CCACHE AND CCACHE_PROGRAM)
+ # Support Unix Makefiles and Ninja
+ set_property(GLOBAL PROPERTY RULE_LAUNCH_COMPILE "${CCACHE_PROGRAM}")
+
+ # Support for Xcode
+ get_property(RULE_LAUNCH_COMPILE GLOBAL PROPERTY RULE_LAUNCH_COMPILE)
+ if(RULE_LAUNCH_COMPILE AND CMAKE_GENERATOR STREQUAL "Xcode")
+ # Set up wrapper scripts
+ configure_file(cmake/templates/launch-c.in launch-c)
+ configure_file(cmake/templates/launch-cxx.in launch-cxx)
+ execute_process(COMMAND chmod a+rx
+ "${CMAKE_BINARY_DIR}/launch-c"
+ "${CMAKE_BINARY_DIR}/launch-cxx")
+
+ # Set Xcode project attributes to route compilation through our scripts
+ set(CMAKE_XCODE_ATTRIBUTE_CC "${CMAKE_BINARY_DIR}/launch-c")
+ set(CMAKE_XCODE_ATTRIBUTE_CXX "${CMAKE_BINARY_DIR}/launch-cxx")
+ set(CMAKE_XCODE_ATTRIBUTE_LD "${CMAKE_BINARY_DIR}/launch-c")
+ set(CMAKE_XCODE_ATTRIBUTE_LDPLUSPLUS "${CMAKE_BINARY_DIR}/launch-cxx")
+ endif()
+endif()
+
diff --git a/software/minizinc/cmake/support/compiler_setup.cmake b/software/minizinc/cmake/support/compiler_setup.cmake
new file mode 100644
index 0000000..02d4ff3
--- /dev/null
+++ b/software/minizinc/cmake/support/compiler_setup.cmake
@@ -0,0 +1,65 @@
+set(CMAKE_CXX_STANDARD 11)
+
+option(USE_ADDRESS_SANITIZER "Use GCC Address Sanitizer" OFF)
+if(USE_ADDRESS_SANITIZER)
+ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=address -fno-omit-frame-pointer")
+ set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -fsanitize=address")
+endif()
+
+set(CMAKE_REQUIRED_QUIET $)
+
+include(CheckCXXCompilerFlag)
+
+set(SAFE_CMAKE_REQUIRED_FLAGS "${CMAKE_REQUIRED_FLAGS}")
+check_cxx_compiler_flag(-Werror HAS_WERROR)
+
+if(HAS_WERROR)
+ set(CMAKE_REQUIRED_FLAGS "${CMAKE_REQUIRED_FLAGS} -Werror")
+endif()
+
+check_cxx_source_compiles("int main(void) { static __thread int x; (void)x; return 0;}" HAS_ATTR_THREAD)
+
+if(NOT HAS_ATTR_THREAD)
+ check_cxx_source_compiles("int main(void) { __declspec(thread) static int x; (void)x; return 0;}" HAS_DECLSPEC_THREAD)
+endif()
+
+check_cxx_source_compiles("#include
+int main(void) { long long int x = atoll(\"123\"); (void)x; }" HAS_ATOLL)
+check_cxx_source_compiles("
+#include
+#include
+#include
+#include
+#include
+#include
+
+int main (int argc, char* argv[])
+{
+ pid_t pid = getpid();
+ char path[PROC_PIDPATHINFO_MAXSIZE];
+ (void) proc_pidpath (pid, path, sizeof(path));
+ return 0;
+}
+" HAS_PIDPATH)
+
+check_cxx_source_compiles("
+#include
+int main (int argc, char* argv[]) {
+ char path[MAX_PATH];
+ (void) GetModuleFileName(NULL, path, MAX_PATH);
+ return 0;
+}" HAS_GETMODULEFILENAME)
+
+check_cxx_source_compiles("
+#include
+int main (int argc, char* argv[]) {
+ (void) GetFileAttributes(NULL);
+ return 0;
+}" HAS_GETFILEATTRIBUTES)
+
+check_cxx_source_compiles("
+#include
+int main (int argc, char* argv[]) {
+ (void) memcpy_s(NULL,0,NULL,0);
+ return 0;
+}" HAS_MEMCPY_S)
diff --git a/software/minizinc/cmake/support/config_emscripten.cmake b/software/minizinc/cmake/support/config_emscripten.cmake
new file mode 100644
index 0000000..9520bd4
--- /dev/null
+++ b/software/minizinc/cmake/support/config_emscripten.cmake
@@ -0,0 +1,58 @@
+if (DEFINED EMSCRIPTEN)
+ add_custom_command(OUTPUT ${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js
+ COMMAND python3 ${EMSCRIPTEN_ROOT_PATH}/tools/file_packager.py minizinc.data --lz4 --preload ${PROJECT_SOURCE_DIR}/share@/minizinc --from-emcc --js-output=${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js
+ COMMENT "building data store minizinc.data")
+
+ set(EMSCRIPTEN_CXX_FLAGS "-s MINIZ_NO_ARCHIVE_APIS -s MINIZ_NO_ZLIB_APIS")
+ set(EMSCRIPTEN_LINK_FLAGS " -s FORCE_FILESYSTEM=1 -s LZ4=1 -s MODULARIZE=1 -s EXTRA_EXPORTED_RUNTIME_METHODS=\"['callMain', 'cwrap', 'FS', 'ENV']\" -s DISABLE_EXCEPTION_CATCHING=0 -s ALLOW_MEMORY_GROWTH=1 --no-heap-copy")
+
+ # -------------------------------------------------------------------------------------------------------------------
+ # -- Web Assembly Configuration.
+
+ # MiniZinc main executable
+ em_link_pre_js(minizinc ${PROJECT_SOURCE_DIR}/cmake/support/emscripten_file_packager_patch.js)
+ em_link_pre_js(minizinc ${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js)
+
+ set_target_properties(minizinc PROPERTIES CXX_FLAGS ${EMSCRIPTEN_CXX_FLAGS})
+ set_target_properties(minizinc PROPERTIES LINK_FLAGS "-s WASM=1 -s EXPORT_NAME=\"'MINIZINC'\" ${EMSCRIPTEN_LINK_FLAGS}")
+
+ install(FILES ${PROJECT_BINARY_DIR}/minizinc.wasm DESTINATION bin)
+ install(FILES ${PROJECT_BINARY_DIR}/minizinc.data DESTINATION bin)
+
+ # mzn2doc executable
+ em_link_pre_js(mzn2doc ${PROJECT_SOURCE_DIR}/cmake/support/emscripten_file_packager_patch.js)
+ em_link_pre_js(mzn2doc ${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js)
+
+ set_target_properties(mzn2doc PROPERTIES CXX_FLAGS ${EMSCRIPTEN_CXX_FLAGS})
+ set_target_properties(mzn2doc PROPERTIES LINK_FLAGS "-s WASM=1 -s EXPORT_NAME=\"'MZN2DOC'\" ${EMSCRIPTEN_LINK_FLAGS}")
+ install(FILES ${PROJECT_BINARY_DIR}/mzn2doc.wasm DESTINATION bin)
+
+ # -------------------------------------------------------------------------------------------------------------------
+ # -- ASM.js (JavaScript) Configuration.
+
+ # MiniZinc main executable
+ add_executable(minizinc_asm minizinc.cpp)
+ target_link_libraries(minizinc_asm mzn)
+
+ em_link_pre_js(minizinc_asm ${PROJECT_SOURCE_DIR}/cmake/support/emscripten_file_packager_patch.js)
+ em_link_pre_js(minizinc_asm ${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js)
+
+ set_target_properties(minizinc_asm PROPERTIES CXX_FLAGS ${EMSCRIPTEN_CXX_FLAGS})
+ set_target_properties(minizinc_asm PROPERTIES LINK_FLAGS "-s WASM=0 -s EXPORT_NAME=\"'MINIZINC'\" ${EMSCRIPTEN_LINK_FLAGS}")
+
+ install(TARGETS minizinc_asm RUNTIME DESTINATION bin)
+ install(FILES $.mem DESTINATION bin)
+
+ # mzn2doc executable
+ add_executable(mzn2doc_asm mzn2doc.cpp)
+ target_link_libraries(mzn2doc_asm mzn)
+
+ em_link_pre_js(mzn2doc_asm ${PROJECT_SOURCE_DIR}/cmake/support/emscripten_file_packager_patch.js)
+ em_link_pre_js(mzn2doc_asm ${PROJECT_BINARY_DIR}/CMakeFiles/file_packager.js)
+
+ set_target_properties(mzn2doc_asm PROPERTIES CXX_FLAGS ${EMSCRIPTEN_CXX_FLAGS})
+ set_target_properties(mzn2doc_asm PROPERTIES LINK_FLAGS "-s WASM=0 -s EXPORT_NAME=\"'MZN2DOC'\" ${EMSCRIPTEN_LINK_FLAGS}")
+
+ install(TARGETS mzn2doc_asm RUNTIME DESTINATION bin)
+ install(FILES $.mem DESTINATION bin)
+endif()
diff --git a/software/minizinc/cmake/support/config_export.cmake b/software/minizinc/cmake/support/config_export.cmake
new file mode 100644
index 0000000..0b8180d
--- /dev/null
+++ b/software/minizinc/cmake/support/config_export.cmake
@@ -0,0 +1,91 @@
+### Export of a CMake configuration for MiniZinc
+## This allows for "find_package(minizinc)"
+
+if(WIN32 AND NOT CYGWIN)
+ set(DEF_INSTALL_CMAKE_DIR CMake)
+else()
+ set(DEF_INSTALL_CMAKE_DIR ${CMAKE_INSTALL_LIBDIR}/cmake)
+endif()
+set(INSTALL_CMAKE_DIR ${DEF_INSTALL_CMAKE_DIR}/libminizinc CACHE PATH "Installation directory for CMake files")
+
+if(NOT IS_ABSOLUTE "${INSTALL_CMAKE_DIR}")
+ set(INSTALL_CMAKE_DIR "${CMAKE_INSTALL_PREFIX}/${INSTALL_CMAKE_DIR}")
+endif()
+
+file(RELATIVE_PATH REL_CMAKE_DIR "${CMAKE_INSTALL_PREFIX}"
+ "${INSTALL_CMAKE_DIR}")
+file(RELATIVE_PATH REL_INCLUDE_DIR "${INSTALL_CMAKE_DIR}"
+ "${CMAKE_INSTALL_PREFIX}/include")
+
+# Add external (static) dependencies
+if(TARGET minizinc_geas)
+ install(
+ FILES cmake/modules/FindGeas.cmake
+ DESTINATION ${REL_CMAKE_DIR}
+ COMPONENT dev
+ )
+ set(CONF_DEPENDENCIES "${CONF_DEPENDENCIES}find_dependency(Geas)\n")
+endif()
+if(TARGET minizinc_gecode)
+ install(
+ FILES cmake/modules/FindGecode.cmake cmake/modules/FindMPFR.cmake
+ DESTINATION ${REL_CMAKE_DIR}
+ COMPONENT dev
+ )
+ if(GECODE_HAS_GIST)
+ set(_CONF_GIST " Gist")
+ endif()
+ set(CONF_DEPENDENCIES "${CONF_DEPENDENCIES}find_dependency(Gecode 6.0 COMPONENTS Driver Float Int Kernel Minimodel Search Set Support${_CONF_GIST})\n")
+endif()
+if(TARGET minizinc_osicbc)
+ install(
+ FILES cmake/modules/FindOsiCBC.cmake
+ DESTINATION ${REL_CMAKE_DIR}
+ COMPONENT dev
+ )
+ set(CONF_DEPENDENCIES "${CONF_DEPENDENCIES}find_dependency(OsiCBC)\n")
+endif()
+
+# Add all targets to the build-tree export set
+export(TARGETS mzn
+ FILE "${PROJECT_BINARY_DIR}/libminizincTargets.cmake")
+
+# Export the package for use from the build-tree
+# (this registers the build-tree with a global CMake-registry)
+export(PACKAGE libminizinc)
+
+# Create the libminizincConfig.cmake and libminizincConfigVersion files
+# ... for the build tree
+set(CONF_INCLUDE_DIRS "${PROJECT_SOURCE_DIR}" "${PROJECT_BINARY_DIR}")
+configure_file(
+ cmake/templates/libminizincConfig.cmake.in
+ "${PROJECT_BINARY_DIR}/libminizincConfig.cmake"
+ @ONLY
+)
+# ... for the install tree
+set(CONF_INCLUDE_DIRS "\${libminizinc_CMAKE_DIR}/${REL_INCLUDE_DIR}")
+configure_file(
+ cmake/templates/libminizincConfig.cmake.in
+ "${PROJECT_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/libminizincConfig.cmake"
+ @ONLY
+)
+# ... for both
+configure_file(
+ cmake/templates/libminizincConfigVersion.cmake.in
+ "${PROJECT_BINARY_DIR}/libminizincConfigVersion.cmake"
+ @ONLY
+)
+
+# Install the libminizincConfig.cmake and libminizincConfigVersion.cmake
+install(
+ FILES "${PROJECT_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/libminizincConfig.cmake" "${PROJECT_BINARY_DIR}/libminizincConfigVersion.cmake"
+ DESTINATION ${REL_CMAKE_DIR}
+ COMPONENT dev
+)
+
+# Install the export set for use with the install-tree
+install(
+ EXPORT libminizincTargets
+ DESTINATION ${REL_CMAKE_DIR}
+ COMPONENT dev
+)
diff --git a/software/minizinc/cmake/support/config_output.cmake b/software/minizinc/cmake/support/config_output.cmake
new file mode 100644
index 0000000..98f3151
--- /dev/null
+++ b/software/minizinc/cmake/support/config_output.cmake
@@ -0,0 +1,35 @@
+message("\n----- MiniZinc build configuration ----")
+if(BUILD_REF)
+ set(STR_BUILD_REF "build ${BUILD_REF}")
+endif()
+message("MiniZinc version: ${libminizinc_VERSION} ${STR_BUILD_REF}")
+message("Enabled drivers:")
+
+if(TARGET minizinc_cplex)
+ if(NOT CPLEX_PLUGIN)
+ set(STR_CPLEX_PLUGIN " (LINKED)")
+ endif()
+ message("\tCPLEX ${CPLEX_VERSION}${STR_CPLEX_PLUGIN}: ${CPLEX_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_geas)
+ message("\tGeas: ${GEAS_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_gecode)
+ message("\tGecode ${GECODE_VERSION}: ${GECODE_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_gurobi)
+ if(NOT GUROBI_PLUGIN)
+ set(STR_GUROBI_PLUGIN " (LINKED)")
+ endif()
+ message("\tGurobi ${GUROBI_VERSION}${STR_GUROBI_PLUGIN}: ${GUROBI_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_osicbc)
+ message("\tOSICBC ${OSICBC_VERSION}: ${OSICBC_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_scip)
+ message("\tSCIP ${SCIP_VERSION}: ${SCIP_INCLUDE_DIRS}")
+endif()
+if(TARGET minizinc_xpress)
+ message("\tXPress: ${XPRESS_INCLUDE_DIRS}")
+endif()
+message("---------------------------------------\n")
\ No newline at end of file
diff --git a/software/minizinc/cmake/support/emscripten_file_packager_patch.js b/software/minizinc/cmake/support/emscripten_file_packager_patch.js
new file mode 100644
index 0000000..a673ba3
--- /dev/null
+++ b/software/minizinc/cmake/support/emscripten_file_packager_patch.js
@@ -0,0 +1,44 @@
+
+function filePackagerPatch_getPreloadedPackageNode(filename) {
+ var fs = require('fs');
+ var path = require('path');
+ filename = path.normalize(path.resolve(__dirname, filename));
+ const buf = fs.readFileSync(filename);
+ // convert to ArrayBuffer
+ return buf.buffer.slice(buf.byteOffset, buf.byteOffset + buf.byteLength);
+}
+
+function filePackagerPatch_isNodeOrShell() {
+ var ENVIRONMENT_IS_WEB = typeof window === 'object';
+ var ENVIRONMENT_IS_WORKER = typeof importScripts === 'function';
+ var ENVIRONMENT_IS_NODE = typeof process === 'object' && typeof require === 'function' && !ENVIRONMENT_IS_WEB && !ENVIRONMENT_IS_WORKER;
+ var ENVIRONMENT_IS_SHELL = !ENVIRONMENT_IS_WEB && !ENVIRONMENT_IS_NODE && !ENVIRONMENT_IS_WORKER;
+ return ENVIRONMENT_IS_NODE || ENVIRONMENT_IS_SHELL;
+}
+
+if (typeof location === 'undefined') {
+ // create a fake location to overrule the file_packager
+ var location = {
+ pathname: '/'
+ };
+}
+
+if (filePackagerPatch_isNodeOrShell()) {
+ Module.getPreloadedPackage = Module.getPreloadedPackage || filePackagerPatch_getPreloadedPackageNode;
+} else {
+ // need a hack to locate relative file in browser settings for the file packager
+ var wrappee = Module.locateFile || function (path, prefix) {return prefix + path};
+ Module.locateFile = function (path, prefix) {
+ if (prefix || !path.endsWith('.data')) {
+ return wrappee(path, prefix);
+ }
+ // file packager is called before a proper script location decection
+ var base = _scriptDir ? _scriptDir : (typeof importScripts === 'function' ? self.location.href : (typeof document !== 'undefined' && document.currentScript ? document.currentScript.src : ''));
+ if (base.indexOf('blob:') !== 0) {
+ base = base.substr(0, base.lastIndexOf('/') + 1);
+ } else {
+ base = '';
+ }
+ return wrappee(path, base);
+ };
+}
diff --git a/software/minizinc/cmake/support/emscripten_setup.cmake b/software/minizinc/cmake/support/emscripten_setup.cmake
new file mode 100644
index 0000000..4c97c8d
--- /dev/null
+++ b/software/minizinc/cmake/support/emscripten_setup.cmake
@@ -0,0 +1,8 @@
+# Workaround for bug in emscripten cmake:
+# add .bc (and on macOS .dylib) as library suffixes
+if (DEFINED EMSCRIPTEN)
+ list(APPEND CMAKE_FIND_LIBRARY_SUFFIXES ".bc")
+ if (CMAKE_HOST_APPLE)
+ list(APPEND CMAKE_FIND_LIBRARY_SUFFIXES ".dylib")
+ endif()
+endif()
diff --git a/software/minizinc/cmake/support/format.cmake b/software/minizinc/cmake/support/format.cmake
new file mode 100644
index 0000000..bc77c2d
--- /dev/null
+++ b/software/minizinc/cmake/support/format.cmake
@@ -0,0 +1,27 @@
+
+if (NOT CLANG_FORMAT_EXECUTABLE)
+ find_program(CLANG_FORMAT_EXECUTABLE NAMES clang-format clang-format-11 clang-format-10 clang-format-9)
+endif()
+
+set(CLANG_FORMAT_FLAGS "-i" CACHE STRING "Flags passed to the clang-format executable")
+
+if (CLANG_FORMAT_EXECUTABLE)
+ file(GLOB_RECURSE FORMAT_FILES
+ ${PROJECT_SOURCE_DIR}/*.c
+ ${PROJECT_SOURCE_DIR}/*.cpp
+ ${PROJECT_SOURCE_DIR}/*.h
+ ${PROJECT_SOURCE_DIR}/*.hh
+ ${PROJECT_SOURCE_DIR}/*.hpp
+ )
+ list(FILTER FORMAT_FILES EXCLUDE REGEX ${PROJECT_BINARY_DIR}/*)
+ list(FILTER FORMAT_FILES EXCLUDE REGEX ${PROJECT_SOURCE_DIR}/lib/cached/*)
+ list(FILTER FORMAT_FILES EXCLUDE REGEX ${PROJECT_SOURCE_DIR}/lib/thirdparty/*)
+ list(FILTER FORMAT_FILES EXCLUDE REGEX ${PROJECT_SOURCE_DIR}/include/minizinc/thirdparty/*)
+
+ separate_arguments(CLANG_FORMAT_FLAGS_LIST NATIVE_COMMAND ${CLANG_FORMAT_FLAGS})
+ add_custom_target(format
+ COMMAND ${CLANG_FORMAT_EXECUTABLE} ${CLANG_FORMAT_FLAGS_LIST} ${FORMAT_FILES}
+ COMMENT "Running ${CLANG_FORMAT_EXECUTABLE} on all source files"
+ )
+endif()
+
diff --git a/software/minizinc/cmake/targets/libminizinc_cplex.cmake b/software/minizinc/cmake/targets/libminizinc_cplex.cmake
new file mode 100644
index 0000000..e8051c5
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_cplex.cmake
@@ -0,0 +1,22 @@
+### MiniZinc CPLEX Solver Target
+
+if(CPLEX_FOUND)
+
+ ### Compile target for the CPlex interface
+ add_library(minizinc_cplex OBJECT
+ solvers/MIP/MIP_cplex_solverfactory.cpp
+ solvers/MIP/MIP_cplex_wrap.cpp
+
+ include/minizinc/solvers/MIP/MIP_cplex_solverfactory.hh
+ include/minizinc/solvers/MIP/MIP_cplex_wrap.hh
+ )
+ set_target_properties(minizinc_cplex PROPERTIES COMPILE_FLAGS ${CPLEX_COMPILE_FLAGS})
+ target_include_directories(minizinc_cplex PRIVATE ${CPLEX_INCLUDE_DIRS})
+ add_dependencies(minizinc_cplex minizinc_mip)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_CPLEX)
+ target_sources(mzn PRIVATE $)
+ set_target_properties(mzn PROPERTIES COMPILE_FLAGS ${CPLEX_COMPILE_FLAGS})
+ target_link_libraries(mzn ${CPLEX_LIBRARIES})
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_fzn.cmake b/software/minizinc/cmake/targets/libminizinc_fzn.cmake
new file mode 100644
index 0000000..795b2e2
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_fzn.cmake
@@ -0,0 +1,14 @@
+### MiniZinc FlatZinc Executable Solver Target
+
+add_library(minizinc_fzn OBJECT
+ solvers/fzn/fzn_solverfactory.cpp
+ solvers/fzn/fzn_solverinstance.cpp
+ solvers/mzn/mzn_solverfactory.cpp
+ solvers/mzn/mzn_solverinstance.cpp
+
+ include/minizinc/solvers/fzn_solverfactory.hh
+ include/minizinc/solvers/fzn_solverinstance.hh
+ include/minizinc/solvers/mzn_solverfactory.hh
+ include/minizinc/solvers/mzn_solverinstance.hh
+)
+add_dependencies(minizinc_fzn minizinc_parser)
diff --git a/software/minizinc/cmake/targets/libminizinc_geas.cmake b/software/minizinc/cmake/targets/libminizinc_geas.cmake
new file mode 100644
index 0000000..8b4c60a
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_geas.cmake
@@ -0,0 +1,23 @@
+### MiniZinc Geas Solver Target
+
+if(GEAS_FOUND)
+
+ ### Compile target for the Geas interface
+ add_library(minizinc_geas OBJECT
+ solvers/geas/geas_constraints.cpp
+ solvers/geas/geas_solverfactory.cpp
+ solvers/geas/geas_solverinstance.cpp
+
+ include/minizinc/solvers/geas/geas_constraints.hh
+ include/minizinc/solvers/geas_solverfactory.hh
+ include/minizinc/solvers/geas_solverinstance.hh
+ )
+ target_include_directories(minizinc_geas PRIVATE "${GEAS_INCLUDE_DIRS}")
+ add_dependencies(minizinc_geas minizinc_parser)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_GEAS)
+ target_sources(mzn PRIVATE $)
+ target_link_libraries(mzn Geas)
+
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_gecode.cmake b/software/minizinc/cmake/targets/libminizinc_gecode.cmake
new file mode 100644
index 0000000..22f25fb
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_gecode.cmake
@@ -0,0 +1,33 @@
+### MiniZinc Gecode Solver Target
+
+if(GECODE_FOUND)
+
+ ### Compile target for the Gecode interface
+ add_library(minizinc_gecode OBJECT
+ lib/passes/gecode_pass.cpp
+
+ solvers/gecode/aux_brancher.hh
+ solvers/gecode/fzn_space.cpp
+ solvers/gecode/gecode_constraints.cpp
+ solvers/gecode/gecode_solverfactory.cpp
+ solvers/gecode/gecode_solverinstance.cpp
+
+ include/minizinc/passes/gecode_pass.hh
+ include/minizinc/solvers/gecode/fzn_space.hh
+ include/minizinc/solvers/gecode/gecode_constraints.hh
+ include/minizinc/solvers/gecode_solverfactory.hh
+ include/minizinc/solvers/gecode_solverinstance.hh
+ )
+ target_include_directories(minizinc_gecode PRIVATE "${GECODE_INCLUDE_DIRS}")
+ add_dependencies(minizinc_gecode minizinc_parser)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_GECODE)
+ target_sources(mzn PRIVATE $)
+
+ target_link_libraries(mzn Gecode::Driver Gecode::Float Gecode::Int Gecode::Kernel Gecode::Search Gecode::Set)
+ if(WIN32 AND GECODE_HAS_GIST)
+ target_link_libraries(mzn Gecode::Gist)
+ endif()
+
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_gurobi.cmake b/software/minizinc/cmake/targets/libminizinc_gurobi.cmake
new file mode 100644
index 0000000..74da1c2
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_gurobi.cmake
@@ -0,0 +1,21 @@
+### MiniZinc Gurobi Solver Target
+
+if(GUROBI_FOUND)
+
+ ### Compile target for the Gurobi interface
+ add_library(minizinc_gurobi OBJECT
+ solvers/MIP/MIP_gurobi_solverfactory.cpp
+ solvers/MIP/MIP_gurobi_wrap.cpp
+
+ include/minizinc/solvers/MIP/MIP_gurobi_solverfactory.hh
+ include/minizinc/solvers/MIP/MIP_gurobi_wrap.hh
+ )
+ target_include_directories(minizinc_gurobi PRIVATE ${GUROBI_INCLUDE_DIRS})
+ add_dependencies(minizinc_gurobi minizinc_mip)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_GUROBI)
+ target_sources(mzn PRIVATE $)
+ target_link_libraries(mzn ${GUROBI_LIBRARIES})
+
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_mip.cmake b/software/minizinc/cmake/targets/libminizinc_mip.cmake
new file mode 100644
index 0000000..cb010bc
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_mip.cmake
@@ -0,0 +1,14 @@
+### Compile target for the base MIP interface
+
+add_library(minizinc_mip OBJECT
+ lib/algorithms/min_cut.cpp
+ lib/utils_savestream.cpp
+
+ solvers/MIP/MIP_solverinstance.cpp
+
+ include/minizinc/plugin.hh
+ include/minizinc/solvers/MIP/MIP_wrap.hh
+ include/minizinc/solvers/MIP/MIP_solverinstance.hh
+ include/minizinc/solvers/MIP/MIP_solverinstance.hpp
+)
+add_dependencies(minizinc_mip minizinc_parser)
diff --git a/software/minizinc/cmake/targets/libminizinc_nl.cmake b/software/minizinc/cmake/targets/libminizinc_nl.cmake
new file mode 100644
index 0000000..87f1eb5
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_nl.cmake
@@ -0,0 +1,16 @@
+### MiniZinc NonLinear Executable Solver Target
+
+add_library(minizinc_nl OBJECT
+ solvers/nl/nl_components.cpp
+ solvers/nl/nl_file.cpp
+ solvers/nl/nl_solreader.cpp
+ solvers/nl/nl_solverfactory.cpp
+ solvers/nl/nl_solverinstance.cpp
+
+ include/minizinc/solvers/nl/nl_components.hh
+ include/minizinc/solvers/nl/nl_file.hh
+ include/minizinc/solvers/nl/nl_solreader.hh
+ include/minizinc/solvers/nl/nl_solverfactory.hh
+ include/minizinc/solvers/nl/nl_solverinstance.hh
+)
+add_dependencies(minizinc_nl minizinc_parser)
diff --git a/software/minizinc/cmake/targets/libminizinc_osicbc.cmake b/software/minizinc/cmake/targets/libminizinc_osicbc.cmake
new file mode 100644
index 0000000..66091ce
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_osicbc.cmake
@@ -0,0 +1,25 @@
+### MiniZinc OsiCBC Solver Target
+
+if(OSICBC_FOUND)
+
+ ### Compile target for the OsiCBC interface
+ add_library(minizinc_osicbc OBJECT
+
+ solvers/MIP/MIP_osicbc_solverfactory.cpp
+ solvers/MIP/MIP_osicbc_wrap.cpp
+
+ include/minizinc/solvers/MIP/MIP_osicbc_solverfactory.hh
+ include/minizinc/solvers/MIP/MIP_osicbc_wrap.hh
+ )
+ target_include_directories(minizinc_osicbc PRIVATE ${OSICBC_INCLUDE_DIRS})
+ add_dependencies(minizinc_osicbc minizinc_mip)
+ if (UNIX AND NOT WIN32)
+ target_compile_definitions(minizinc_osicbc PRIVATE HAVE_CONFIG_H)
+ endif()
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_OSICBC)
+ target_sources(mzn PRIVATE $)
+ target_link_libraries(mzn ${OSICBC_TARGETS})
+
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_parser.cmake b/software/minizinc/cmake/targets/libminizinc_parser.cmake
new file mode 100644
index 0000000..8f5663a
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_parser.cmake
@@ -0,0 +1,114 @@
+# -------------------------------------------------------------------------------------------------------------------
+## Parser Generation Targets
+
+# When updating the cached files, update MD5 sums defined in this file
+include(${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake)
+
+macro(MD5 filename md5sum)
+ file(READ "${filename}" RAW_MD5_FILE)
+ string(REGEX REPLACE "\r" "" STRIPPED_MD5_FILE "${RAW_MD5_FILE}")
+ string(MD5 ${md5sum} "${STRIPPED_MD5_FILE}")
+endmacro(MD5)
+
+find_package(BISON 3.4)
+find_package(FLEX 2.5)
+
+if(BISON_FOUND AND FLEX_FOUND)
+ BISON_TARGET(MZNParser
+ ${PROJECT_SOURCE_DIR}/lib/parser.yxx
+ ${PROJECT_BINARY_DIR}/parser.tab.cpp
+ DEFINES_FILE ${PROJECT_BINARY_DIR}/include/minizinc/parser.tab.hh
+ COMPILE_FLAGS "-p mzn_yy -l"
+ )
+
+ file(MAKE_DIRECTORY ${PROJECT_BINARY_DIR}/include/minizinc/support/)
+ BISON_TARGET(RegExParser
+ ${PROJECT_SOURCE_DIR}/lib/support/regex/parser.yxx
+ ${PROJECT_BINARY_DIR}/regex_parser.tab.cpp
+ DEFINES_FILE ${PROJECT_BINARY_DIR}/include/minizinc/support/regex_parser.tab.hh
+ COMPILE_FLAGS "-p regex_yy -l"
+ )
+
+ FLEX_TARGET(MZNLexer
+ ${PROJECT_SOURCE_DIR}/lib/lexer.lxx
+ ${PROJECT_BINARY_DIR}/lexer.yy.cpp
+ COMPILE_FLAGS "-P mzn_yy -L"
+ )
+ ADD_FLEX_BISON_DEPENDENCY(MZNLexer MZNParser)
+
+ FLEX_TARGET(RegExLexer
+ ${PROJECT_SOURCE_DIR}/lib/support/regex/lexer.lxx
+ ${PROJECT_BINARY_DIR}/regex_lexer.yy.cpp
+ COMPILE_FLAGS "-P regex_yy -L"
+ )
+ ADD_FLEX_BISON_DEPENDENCY(RegExLexer RegExParser)
+else()
+ MD5(${PROJECT_SOURCE_DIR}/lib/parser.yxx parser_yxx_md5)
+ if(NOT "${parser_yxx_md5}" STREQUAL "${parser_yxx_md5_cached}")
+ message(FATAL_ERROR
+ "The file parser.yxx has been modified but bison cannot be run.\n"
+ "If you are sure parser.tab.cpp and minizinc/parser.tab.hh in ${PROJECT_SOURCE_DIR}/lib/cached/ are correct "
+ "then copy parser.yxx's md5 ${parser_yxx_md5} into ${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake"
+ )
+ endif()
+
+ MD5(${PROJECT_SOURCE_DIR}/lib/support/regex/parser.yxx regex_parser_yxx_md5)
+ if(NOT "${regex_parser_yxx_md5}" STREQUAL "${regex_parser_yxx_md5_cached}")
+ message(FATAL_ERROR
+ "The file regex/parser.yxx has been modified but bison cannot be run.\n"
+ "If you are sure regex_parser.tab.cpp and minizinc/support/regex_parser.tab.hh in "
+ "${PROJECT_SOURCE_DIR}/lib/cached/ are correct then copy regex_parser.yxx's md5 ${regex_parser_yxx_md5} into "
+ "${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake"
+ )
+ endif()
+
+ MD5(${PROJECT_SOURCE_DIR}/lib/lexer.lxx lexer_lxx_md5)
+ if(NOT "${lexer_lxx_md5}" STREQUAL "${lexer_lxx_md5_cached}")
+ message(FATAL_ERROR
+ "The file lexer.lxx has been modified but flex cannot be run.\n"
+ "If you are sure ${PROJECT_SOURCE_DIR}/lib/cached/lexer.yy.cpp is correct then "
+ "copy lexer.lxx's md5 ${lexer_lxx_md5} into ${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake"
+ )
+ endif()
+
+ MD5(${PROJECT_SOURCE_DIR}/lib/support/regex/lexer.lxx regex_lexer_lxx_md5)
+ if(NOT "${regex_lexer_lxx_md5}" STREQUAL "${regex_lexer_lxx_md5_cached}")
+ message(FATAL_ERROR
+ "The file regex/lexer.lxx has been modified but flex cannot be run.\n"
+ "If you are sure ${PROJECT_SOURCE_DIR}/lib/cached/regex_lexer.yy.cpp is correct then "
+ "copy regex/lexer.lxx's md5 ${regex_lexer_lxx_md5} into ${PROJECT_SOURCE_DIR}/lib/cached/md5_cached.cmake"
+ )
+ endif()
+
+ include_directories(${PROJECT_SOURCE_DIR}/lib/cached)
+ set(BISON_MZNParser_OUTPUTS
+ ${PROJECT_SOURCE_DIR}/lib/cached/parser.tab.cpp
+ ${PROJECT_SOURCE_DIR}/lib/cached/minizinc/parser.tab.hh
+ )
+ set(BISON_RegExParser_OUTPUTS
+ ${PROJECT_SOURCE_DIR}/lib/cached/regex_parser.tab.cpp
+ ${PROJECT_SOURCE_DIR}/lib/cached/minizinc/support/regex_parser.tab.hh
+ )
+ set(FLEX_MZNLexer_OUTPUTS ${PROJECT_SOURCE_DIR}/lib/cached/lexer.yy.cpp)
+ set(FLEX_RegExLexer_OUTPUTS ${PROJECT_SOURCE_DIR}/lib/cached/regex_lexer.yy.cpp)
+endif()
+
+if(NOT GECODE_FOUND)
+ set(FLEX_RegExLexer_OUTPUTS "")
+ set(BISON_RegExParser_OUTPUTS "")
+endif()
+
+add_library(minizinc_parser OBJECT
+ ${BISON_MZNParser_OUTPUTS}
+ ${FLEX_MZNLexer_OUTPUTS}
+ ${BISON_RegExParser_OUTPUTS}
+ ${FLEX_RegExLexer_OUTPUTS}
+)
+set_target_properties(minizinc_parser PROPERTIES
+ CXX_CLANG_TIDY ""
+)
+
+if(GECODE_FOUND)
+ target_include_directories(minizinc_parser PRIVATE "${GECODE_INCLUDE_DIRS}")
+ target_compile_definitions(minizinc_parser PRIVATE HAS_GECODE)
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_scip.cmake b/software/minizinc/cmake/targets/libminizinc_scip.cmake
new file mode 100644
index 0000000..8b30c82
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_scip.cmake
@@ -0,0 +1,20 @@
+### MiniZinc SCIP Solver Target
+
+if(SCIP_FOUND)
+
+ ### Compile target for the SCIP interface
+ add_library(minizinc_scip OBJECT
+ solvers/MIP/MIP_scip_solverfactory.cpp
+ solvers/MIP/MIP_scip_wrap.cpp
+
+ include/minizinc/solvers/MIP/MIP_scip_solverfactory.hh
+ include/minizinc/solvers/MIP/MIP_scip_wrap.hh
+ )
+ target_include_directories(minizinc_scip PRIVATE ${SCIP_INCLUDE_DIRS})
+ add_dependencies(minizinc_scip minizinc_mip)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_SCIP)
+ target_sources(mzn PRIVATE $)
+
+endif()
diff --git a/software/minizinc/cmake/targets/libminizinc_xpress.cmake b/software/minizinc/cmake/targets/libminizinc_xpress.cmake
new file mode 100644
index 0000000..4be2da0
--- /dev/null
+++ b/software/minizinc/cmake/targets/libminizinc_xpress.cmake
@@ -0,0 +1,21 @@
+### MiniZinc FICO Xpress Solver Target
+
+if(XPRESS_FOUND)
+
+ ### Compile target for the Xpress interface
+ add_library(minizinc_xpress OBJECT
+ solvers/MIP/MIP_xpress_solverfactory.cpp
+ solvers/MIP/MIP_xpress_wrap.cpp
+
+ include/minizinc/solvers/MIP/MIP_xpress_solverfactory.hh
+ include/minizinc/solvers/MIP/MIP_xpress_wrap.hh
+ )
+
+ target_include_directories(minizinc_xpress PRIVATE ${XPRESS_INCLUDE_DIRS})
+ add_dependencies(minizinc_xpress minizinc_mip)
+
+ ### Setup correct compilation into the MiniZinc library
+ target_compile_definitions(mzn PRIVATE HAS_XPRESS)
+ target_sources(mzn PRIVATE $)
+
+endif()
diff --git a/software/minizinc/cmake/targets/libmzn.cmake b/software/minizinc/cmake/targets/libmzn.cmake
new file mode 100644
index 0000000..b900956
--- /dev/null
+++ b/software/minizinc/cmake/targets/libmzn.cmake
@@ -0,0 +1,158 @@
+### MiniZinc Library Target
+# Combined definition of the MiniZinc core and all solvers compiled
+
+include(cmake/targets/libminizinc_parser.cmake)
+include(cmake/targets/libminizinc_fzn.cmake)
+include(cmake/targets/libminizinc_nl.cmake)
+include(cmake/targets/libminizinc_mip.cmake)
+
+add_library(mzn
+ lib/MIPdomains.cpp
+ lib/ast.cpp
+ lib/astexception.cpp
+ lib/astmap.cpp
+ lib/aststring.cpp
+ lib/astvec.cpp
+ lib/builtins.cpp
+ lib/cdecode.c
+ lib/cencode.c
+ lib/chain_compressor.cpp
+ lib/copy.cpp
+ lib/eval_par.cpp
+ lib/file_utils.cpp
+ lib/flatten.cpp
+ lib/flatten/flat_exp.cpp
+ lib/flatten/flatten_anon.cpp
+ lib/flatten/flatten_arrayaccess.cpp
+ lib/flatten/flatten_arraylit.cpp
+ lib/flatten/flatten_binop.cpp
+ lib/flatten/flatten_call.cpp
+ lib/flatten/flatten_comp.cpp
+ lib/flatten/flatten_id.cpp
+ lib/flatten/flatten_ite.cpp
+ lib/flatten/flatten_let.cpp
+ lib/flatten/flatten_par.cpp
+ lib/flatten/flatten_setlit.cpp
+ lib/flatten/flatten_unop.cpp
+ lib/flatten/flatten_vardecl.cpp
+ lib/flattener.cpp
+ lib/gc.cpp
+ lib/htmlprinter.cpp
+ lib/json_parser.cpp
+ lib/lexer.lxx
+ lib/thirdparty/miniz.c
+ lib/model.cpp
+ lib/optimize.cpp
+ lib/optimize_constraints.cpp
+ lib/output.cpp
+ lib/param_config.cpp
+ lib/parser.cpp
+ lib/parser.yxx
+ lib/passes/compile_pass.cpp
+ lib/pathfileprinter.cpp
+ lib/prettyprinter.cpp
+ lib/solns2out.cpp
+ lib/solver.cpp
+ lib/solver_config.cpp
+ lib/solver_instance_base.cpp
+ lib/statistics.cpp
+ lib/type.cpp
+ lib/typecheck.cpp
+ lib/values.cpp
+ lib/support/regex/parser.yxx
+ lib/support/regex/lexer.lxx
+
+ include/minizinc/ast.hh
+ include/minizinc/ast.hpp
+ include/minizinc/astexception.hh
+ include/minizinc/astiterator.hh
+ include/minizinc/astmap.hh
+ include/minizinc/aststring.hh
+ include/minizinc/astvec.hh
+ include/minizinc/builtins.hh
+ include/minizinc/chain_compressor.hh
+ include/minizinc/config.hh.in
+ include/minizinc/copy.hh
+ include/minizinc/eval_par.hh
+ include/minizinc/exception.hh
+ include/minizinc/file_utils.hh
+ include/minizinc/flat_exp.hh
+ include/minizinc/flatten.hh
+ include/minizinc/flatten_internal.hh
+ include/minizinc/flattener.hh
+ include/minizinc/gc.hh
+ include/minizinc/hash.hh
+ include/minizinc/htmlprinter.hh
+ include/minizinc/interrupt.hh
+ include/minizinc/iter.hh
+ include/minizinc/json_parser.hh
+ include/minizinc/model.hh
+ include/minizinc/optimize.hh
+ include/minizinc/optimize_constraints.hh
+ include/minizinc/output.hh
+ include/minizinc/param_config.hh
+ include/minizinc/parser.hh
+ include/minizinc/passes/compile_pass.hh
+ include/minizinc/pathfileprinter.hh
+ include/minizinc/prettyprinter.hh
+ include/minizinc/process.hh
+ include/minizinc/solns2out.hh
+ include/minizinc/solver.hh
+ include/minizinc/solver_config.hh
+ include/minizinc/solver_instance.hh
+ include/minizinc/solver_instance_base.hh
+ include/minizinc/statistics.hh
+ include/minizinc/support/regex.hh
+ include/minizinc/_thirdparty/b64/cdecode.h
+ include/minizinc/_thirdparty/b64/cencode.h
+ include/minizinc/_thirdparty/b64/decode.h
+ include/minizinc/_thirdparty/b64/encode.h
+ include/minizinc/_thirdparty/miniz.h
+ include/minizinc/timer.hh
+ include/minizinc/type.hh
+ include/minizinc/typecheck.hh
+ include/minizinc/utils.hh
+ include/minizinc/values.hh
+
+ $
+ $
+ $
+ $
+)
+target_link_libraries(mzn ${CMAKE_THREAD_LIBS_INIT})
+
+### Add Solver Interfaces to the MiniZinc library when available
+include(cmake/targets/libminizinc_cplex.cmake)
+include(cmake/targets/libminizinc_geas.cmake)
+include(cmake/targets/libminizinc_gecode.cmake)
+include(cmake/targets/libminizinc_gurobi.cmake)
+include(cmake/targets/libminizinc_osicbc.cmake)
+include(cmake/targets/libminizinc_scip.cmake)
+include(cmake/targets/libminizinc_xpress.cmake)
+
+if(GECODE_FOUND)
+ target_link_libraries(mzn Gecode::Minimodel Gecode::Support)
+endif()
+
+
+### Add all necessary files to the install target
+install(
+ TARGETS mzn
+ EXPORT libminizincTargets
+ RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
+ LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
+ ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
+)
+install(
+ DIRECTORY share/minizinc
+ DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}
+)
+install(
+ DIRECTORY include/minizinc
+ DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
+ PATTERN config.hh.in EXCLUDE
+)
+install(
+ DIRECTORY lib/cached/minizinc
+ DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
+)
diff --git a/software/minizinc/cmake/targets/minizinc.cmake b/software/minizinc/cmake/targets/minizinc.cmake
new file mode 100644
index 0000000..a2a4668
--- /dev/null
+++ b/software/minizinc/cmake/targets/minizinc.cmake
@@ -0,0 +1,12 @@
+#### MiniZinc Executable Target
+
+add_executable(minizinc minizinc.cpp)
+target_link_libraries(minizinc mzn)
+
+install(
+ TARGETS minizinc
+ EXPORT libminizincTargets
+ RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
+ LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
+ ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
+)
diff --git a/software/minizinc/cmake/targets/mzn2doc.cmake b/software/minizinc/cmake/targets/mzn2doc.cmake
new file mode 100644
index 0000000..9648900
--- /dev/null
+++ b/software/minizinc/cmake/targets/mzn2doc.cmake
@@ -0,0 +1,11 @@
+#### Binary target for MiniZinc documentation generator
+add_executable(mzn2doc mzn2doc.cpp)
+target_link_libraries(mzn2doc mzn)
+
+install(
+ TARGETS mzn2doc
+ EXPORT libminizincTargets
+ RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
+ LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
+ ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
+)
diff --git a/software/minizinc/cmake/templates/launch-c.in b/software/minizinc/cmake/templates/launch-c.in
new file mode 100644
index 0000000..3d476af
--- /dev/null
+++ b/software/minizinc/cmake/templates/launch-c.in
@@ -0,0 +1,3 @@
+#!/bin/sh
+export CCACHE_CPP2=true
+exec "${RULE_LAUNCH_COMPILE}" "${CMAKE_C_COMPILER}" "$@"
\ No newline at end of file
diff --git a/software/minizinc/cmake/templates/launch-cxx.in b/software/minizinc/cmake/templates/launch-cxx.in
new file mode 100644
index 0000000..039edb0
--- /dev/null
+++ b/software/minizinc/cmake/templates/launch-cxx.in
@@ -0,0 +1,3 @@
+#!/bin/sh
+export CCACHE_CPP2=true
+exec "${RULE_LAUNCH_COMPILE}" "${CMAKE_CXX_COMPILER}" "$@"
\ No newline at end of file
diff --git a/software/minizinc/cmake/templates/libminizincConfig.cmake.in b/software/minizinc/cmake/templates/libminizincConfig.cmake.in
new file mode 100644
index 0000000..730a4d7
--- /dev/null
+++ b/software/minizinc/cmake/templates/libminizincConfig.cmake.in
@@ -0,0 +1,18 @@
+# - Config file for the libminizinc package
+# It defines the following variables
+# libminizinc_INCLUDE_DIRS - include directories for libminizinc
+# libminizinc_LIBRARIES - libraries to link against
+# libminizinc_EXECUTABLE - the bar executable
+
+# Compute paths
+get_filename_component(libminizinc_CMAKE_DIR "${CMAKE_CURRENT_LIST_FILE}" PATH)
+set(libminizinc_INCLUDE_DIRS "@CONF_INCLUDE_DIRS@")
+
+# Our library dependencies
+list(APPEND CMAKE_MODULE_PATH ${libminizinc_CMAKE_DIR})
+include(CMakeFindDependencyMacro)
+@CONF_DEPENDENCIES@
+
+# Our library targets (contains definitions for IMPORTED targets)
+include("${libminizinc_CMAKE_DIR}/libminizincTargets.cmake")
+
diff --git a/software/minizinc/cmake/templates/libminizincConfigVersion.cmake.in b/software/minizinc/cmake/templates/libminizincConfigVersion.cmake.in
new file mode 100644
index 0000000..00ae7c9
--- /dev/null
+++ b/software/minizinc/cmake/templates/libminizincConfigVersion.cmake.in
@@ -0,0 +1,12 @@
+set(PACKAGE_VERSION "@libminizinc_VERSION@")
+
+# Check whether the requested PACKAGE_FIND_VERSION is compatible
+if("${PACKAGE_VERSION}" VERSION_LESS "${PACKAGE_FIND_VERSION}")
+ set(PACKAGE_VERSION_COMPATIBLE FALSE)
+else()
+ set(PACKAGE_VERSION_COMPATIBLE TRUE)
+ if ("${PACKAGE_VERSION}" VERSION_EQUAL "${PACKAGE_FIND_VERSION}")
+ set(PACKAGE_VERSION_EXACT TRUE)
+ endif()
+endif()
+
diff --git a/software/minizinc/docs/LICENSE.txt b/software/minizinc/docs/LICENSE.txt
new file mode 100644
index 0000000..c2df958
--- /dev/null
+++ b/software/minizinc/docs/LICENSE.txt
@@ -0,0 +1,390 @@
+Attribution-NoDerivatives 4.0 International
+
+=======================================================================
+
+Creative Commons Corporation ("Creative Commons") is not a law firm and
+does not provide legal services or legal advice. Distribution of
+Creative Commons public licenses does not create a lawyer-client or
+other relationship. Creative Commons makes its licenses and related
+information available on an "as-is" basis. Creative Commons gives no
+warranties regarding its licenses, any material licensed under their
+terms and conditions, or any related information. Creative Commons
+disclaims all liability for damages resulting from their use to the
+fullest extent possible.
+
+Using Creative Commons Public Licenses
+
+Creative Commons public licenses provide a standard set of terms and
+conditions that creators and other rights holders may use to share
+original works of authorship and other material subject to copyright
+and certain other rights specified in the public license below. The
+following considerations are for informational purposes only, are not
+exhaustive, and do not form part of our licenses.
+
+ Considerations for licensors: Our public licenses are
+ intended for use by those authorized to give the public
+ permission to use material in ways otherwise restricted by
+ copyright and certain other rights. Our licenses are
+ irrevocable. Licensors should read and understand the terms
+ and conditions of the license they choose before applying it.
+ Licensors should also secure all rights necessary before
+ applying our licenses so that the public can reuse the
+ material as expected. Licensors should clearly mark any
+ material not subject to the license. This includes other CC-
+ licensed material, or material used under an exception or
+ limitation to copyright. More considerations for licensors:
+ wiki.creativecommons.org/Considerations_for_licensors
+
+ Considerations for the public: By using one of our public
+ licenses, a licensor grants the public permission to use the
+ licensed material under specified terms and conditions. If
+ the licensor's permission is not necessary for any reason--for
+ example, because of any applicable exception or limitation to
+ copyright--then that use is not regulated by the license. Our
+ licenses grant only permissions under copyright and certain
+ other rights that a licensor has authority to grant. Use of
+ the licensed material may still be restricted for other
+ reasons, including because others have copyright or other
+ rights in the material. A licensor may make special requests,
+ such as asking that all changes be marked or described.
+ Although not required by our licenses, you are encouraged to
+ respect those requests where reasonable. More considerations
+ for the public:
+ wiki.creativecommons.org/Considerations_for_licensees
+
+
+=======================================================================
+
+Creative Commons Attribution-NoDerivatives 4.0 International Public
+License
+
+By exercising the Licensed Rights (defined below), You accept and agree
+to be bound by the terms and conditions of this Creative Commons
+Attribution-NoDerivatives 4.0 International Public License ("Public
+License"). To the extent this Public License may be interpreted as a
+contract, You are granted the Licensed Rights in consideration of Your
+acceptance of these terms and conditions, and the Licensor grants You
+such rights in consideration of benefits the Licensor receives from
+making the Licensed Material available under these terms and
+conditions.
+
+
+Section 1 -- Definitions.
+
+ a. Adapted Material means material subject to Copyright and Similar
+ Rights that is derived from or based upon the Licensed Material
+ and in which the Licensed Material is translated, altered,
+ arranged, transformed, or otherwise modified in a manner requiring
+ permission under the Copyright and Similar Rights held by the
+ Licensor. For purposes of this Public License, where the Licensed
+ Material is a musical work, performance, or sound recording,
+ Adapted Material is always produced where the Licensed Material is
+ synched in timed relation with a moving image.
+
+ b. Copyright and Similar Rights means copyright and/or similar rights
+ closely related to copyright including, without limitation,
+ performance, broadcast, sound recording, and Sui Generis Database
+ Rights, without regard to how the rights are labeled or
+ categorized. For purposes of this Public License, the rights
+ specified in Section 2(b)(1)-(2) are not Copyright and Similar
+ Rights.
+
+ c. Effective Technological Measures means those measures that, in the
+ absence of proper authority, may not be circumvented under laws
+ fulfilling obligations under Article 11 of the WIPO Copyright
+ Treaty adopted on December 20, 1996, and/or similar international
+ agreements.
+
+ d. Exceptions and Limitations means fair use, fair dealing, and/or
+ any other exception or limitation to Copyright and Similar Rights
+ that applies to Your use of the Licensed Material.
+
+ e. Licensed Material means the artistic or literary work, database,
+ or other material to which the Licensor applied this Public
+ License.
+
+ f. Licensed Rights means the rights granted to You subject to the
+ terms and conditions of this Public License, which are limited to
+ all Copyright and Similar Rights that apply to Your use of the
+ Licensed Material and that the Licensor has authority to license.
+
+ g. Licensor means the individual(s) or entity(ies) granting rights
+ under this Public License.
+
+ h. Share means to provide material to the public by any means or
+ process that requires permission under the Licensed Rights, such
+ as reproduction, public display, public performance, distribution,
+ dissemination, communication, or importation, and to make material
+ available to the public including in ways that members of the
+ public may access the material from a place and at a time
+ individually chosen by them.
+
+ i. Sui Generis Database Rights means rights other than copyright
+ resulting from Directive 96/9/EC of the European Parliament and of
+ the Council of 11 March 1996 on the legal protection of databases,
+ as amended and/or succeeded, as well as other essentially
+ equivalent rights anywhere in the world.
+
+ j. You means the individual or entity exercising the Licensed Rights
+ under this Public License. Your has a corresponding meaning.
+
+
+Section 2 -- Scope.
+
+ a. License grant.
+
+ 1. Subject to the terms and conditions of this Public License,
+ the Licensor hereby grants You a worldwide, royalty-free,
+ non-sublicensable, non-exclusive, irrevocable license to
+ exercise the Licensed Rights in the Licensed Material to:
+
+ a. reproduce and Share the Licensed Material, in whole or
+ in part; and
+
+ b. produce and reproduce, but not Share, Adapted Material.
+
+ 2. Exceptions and Limitations. For the avoidance of doubt, where
+ Exceptions and Limitations apply to Your use, this Public
+ License does not apply, and You do not need to comply with
+ its terms and conditions.
+
+ 3. Term. The term of this Public License is specified in Section
+ 6(a).
+
+ 4. Media and formats; technical modifications allowed. The
+ Licensor authorizes You to exercise the Licensed Rights in
+ all media and formats whether now known or hereafter created,
+ and to make technical modifications necessary to do so. The
+ Licensor waives and/or agrees not to assert any right or
+ authority to forbid You from making technical modifications
+ necessary to exercise the Licensed Rights, including
+ technical modifications necessary to circumvent Effective
+ Technological Measures. For purposes of this Public License,
+ simply making modifications authorized by this Section 2(a)
+ (4) never produces Adapted Material.
+
+ 5. Downstream recipients.
+
+ a. Offer from the Licensor -- Licensed Material. Every
+ recipient of the Licensed Material automatically
+ receives an offer from the Licensor to exercise the
+ Licensed Rights under the terms and conditions of this
+ Public License.
+
+ b. No downstream restrictions. You may not offer or impose
+ any additional or different terms or conditions on, or
+ apply any Effective Technological Measures to, the
+ Licensed Material if doing so restricts exercise of the
+ Licensed Rights by any recipient of the Licensed
+ Material.
+
+ 6. No endorsement. Nothing in this Public License constitutes or
+ may be construed as permission to assert or imply that You
+ are, or that Your use of the Licensed Material is, connected
+ with, or sponsored, endorsed, or granted official status by,
+ the Licensor or others designated to receive attribution as
+ provided in Section 3(a)(1)(A)(i).
+
+ b. Other rights.
+
+ 1. Moral rights, such as the right of integrity, are not
+ licensed under this Public License, nor are publicity,
+ privacy, and/or other similar personality rights; however, to
+ the extent possible, the Licensor waives and/or agrees not to
+ assert any such rights held by the Licensor to the limited
+ extent necessary to allow You to exercise the Licensed
+ Rights, but not otherwise.
+
+ 2. Patent and trademark rights are not licensed under this
+ Public License.
+
+ 3. To the extent possible, the Licensor waives any right to
+ collect royalties from You for the exercise of the Licensed
+ Rights, whether directly or through a collecting society
+ under any voluntary or waivable statutory or compulsory
+ licensing scheme. In all other cases the Licensor expressly
+ reserves any right to collect such royalties.
+
+
+Section 3 -- License Conditions.
+
+Your exercise of the Licensed Rights is expressly made subject to the
+following conditions.
+
+ a. Attribution.
+
+ 1. If You Share the Licensed Material, You must:
+
+ a. retain the following if it is supplied by the Licensor
+ with the Licensed Material:
+
+ i. identification of the creator(s) of the Licensed
+ Material and any others designated to receive
+ attribution, in any reasonable manner requested by
+ the Licensor (including by pseudonym if
+ designated);
+
+ ii. a copyright notice;
+
+ iii. a notice that refers to this Public License;
+
+ iv. a notice that refers to the disclaimer of
+ warranties;
+
+ v. a URI or hyperlink to the Licensed Material to the
+ extent reasonably practicable;
+
+ b. indicate if You modified the Licensed Material and
+ retain an indication of any previous modifications; and
+
+ c. indicate the Licensed Material is licensed under this
+ Public License, and include the text of, or the URI or
+ hyperlink to, this Public License.
+
+ For the avoidance of doubt, You do not have permission under
+ this Public License to Share Adapted Material.
+
+ 2. You may satisfy the conditions in Section 3(a)(1) in any
+ reasonable manner based on the medium, means, and context in
+ which You Share the Licensed Material. For example, it may be
+ reasonable to satisfy the conditions by providing a URI or
+ hyperlink to a resource that includes the required
+ information.
+
+ 3. If requested by the Licensor, You must remove any of the
+ information required by Section 3(a)(1)(A) to the extent
+ reasonably practicable.
+
+
+Section 4 -- Sui Generis Database Rights.
+
+Where the Licensed Rights include Sui Generis Database Rights that
+apply to Your use of the Licensed Material:
+
+ a. for the avoidance of doubt, Section 2(a)(1) grants You the right
+ to extract, reuse, reproduce, and Share all or a substantial
+ portion of the contents of the database, provided You do not Share
+ Adapted Material;
+ b. if You include all or a substantial portion of the database
+ contents in a database in which You have Sui Generis Database
+ Rights, then the database in which You have Sui Generis Database
+ Rights (but not its individual contents) is Adapted Material; and
+ c. You must comply with the conditions in Section 3(a) if You Share
+ all or a substantial portion of the contents of the database.
+
+For the avoidance of doubt, this Section 4 supplements and does not
+replace Your obligations under this Public License where the Licensed
+Rights include other Copyright and Similar Rights.
+
+
+Section 5 -- Disclaimer of Warranties and Limitation of Liability.
+
+ a. UNLESS OTHERWISE SEPARATELY UNDERTAKEN BY THE LICENSOR, TO THE
+ EXTENT POSSIBLE, THE LICENSOR OFFERS THE LICENSED MATERIAL AS-IS
+ AND AS-AVAILABLE, AND MAKES NO REPRESENTATIONS OR WARRANTIES OF
+ ANY KIND CONCERNING THE LICENSED MATERIAL, WHETHER EXPRESS,
+ IMPLIED, STATUTORY, OR OTHER. THIS INCLUDES, WITHOUT LIMITATION,
+ WARRANTIES OF TITLE, MERCHANTABILITY, FITNESS FOR A PARTICULAR
+ PURPOSE, NON-INFRINGEMENT, ABSENCE OF LATENT OR OTHER DEFECTS,
+ ACCURACY, OR THE PRESENCE OR ABSENCE OF ERRORS, WHETHER OR NOT
+ KNOWN OR DISCOVERABLE. WHERE DISCLAIMERS OF WARRANTIES ARE NOT
+ ALLOWED IN FULL OR IN PART, THIS DISCLAIMER MAY NOT APPLY TO YOU.
+
+ b. TO THE EXTENT POSSIBLE, IN NO EVENT WILL THE LICENSOR BE LIABLE
+ TO YOU ON ANY LEGAL THEORY (INCLUDING, WITHOUT LIMITATION,
+ NEGLIGENCE) OR OTHERWISE FOR ANY DIRECT, SPECIAL, INDIRECT,
+ INCIDENTAL, CONSEQUENTIAL, PUNITIVE, EXEMPLARY, OR OTHER LOSSES,
+ COSTS, EXPENSES, OR DAMAGES ARISING OUT OF THIS PUBLIC LICENSE OR
+ USE OF THE LICENSED MATERIAL, EVEN IF THE LICENSOR HAS BEEN
+ ADVISED OF THE POSSIBILITY OF SUCH LOSSES, COSTS, EXPENSES, OR
+ DAMAGES. WHERE A LIMITATION OF LIABILITY IS NOT ALLOWED IN FULL OR
+ IN PART, THIS LIMITATION MAY NOT APPLY TO YOU.
+
+ c. The disclaimer of warranties and limitation of liability provided
+ above shall be interpreted in a manner that, to the extent
+ possible, most closely approximates an absolute disclaimer and
+ waiver of all liability.
+
+
+Section 6 -- Term and Termination.
+
+ a. This Public License applies for the term of the Copyright and
+ Similar Rights licensed here. However, if You fail to comply with
+ this Public License, then Your rights under this Public License
+ terminate automatically.
+
+ b. Where Your right to use the Licensed Material has terminated under
+ Section 6(a), it reinstates:
+
+ 1. automatically as of the date the violation is cured, provided
+ it is cured within 30 days of Your discovery of the
+ violation; or
+
+ 2. upon express reinstatement by the Licensor.
+
+ For the avoidance of doubt, this Section 6(b) does not affect any
+ right the Licensor may have to seek remedies for Your violations
+ of this Public License.
+
+ c. For the avoidance of doubt, the Licensor may also offer the
+ Licensed Material under separate terms or conditions or stop
+ distributing the Licensed Material at any time; however, doing so
+ will not terminate this Public License.
+
+ d. Sections 1, 5, 6, 7, and 8 survive termination of this Public
+ License.
+
+
+Section 7 -- Other Terms and Conditions.
+
+ a. The Licensor shall not be bound by any additional or different
+ terms or conditions communicated by You unless expressly agreed.
+
+ b. Any arrangements, understandings, or agreements regarding the
+ Licensed Material not stated herein are separate from and
+ independent of the terms and conditions of this Public License.
+
+
+Section 8 -- Interpretation.
+
+ a. For the avoidance of doubt, this Public License does not, and
+ shall not be interpreted to, reduce, limit, restrict, or impose
+ conditions on any use of the Licensed Material that could lawfully
+ be made without permission under this Public License.
+
+ b. To the extent possible, if any provision of this Public License is
+ deemed unenforceable, it shall be automatically reformed to the
+ minimum extent necessary to make it enforceable. If the provision
+ cannot be reformed, it shall be severed from this Public License
+ without affecting the enforceability of the remaining terms and
+ conditions.
+
+ c. No term or condition of this Public License will be waived and no
+ failure to comply consented to unless expressly agreed to by the
+ Licensor.
+
+ d. Nothing in this Public License constitutes or may be interpreted
+ as a limitation upon, or waiver of, any privileges and immunities
+ that apply to the Licensor or You, including from the legal
+ processes of any jurisdiction or authority.
+
+=======================================================================
+
+Creative Commons is not a party to its public
+licenses. Notwithstanding, Creative Commons may elect to apply one of
+its public licenses to material it publishes and in those instances
+will be considered the “Licensor.” The text of the Creative Commons
+public licenses is dedicated to the public domain under the CC0 Public
+Domain Dedication. Except for the limited purpose of indicating that
+material is shared under a Creative Commons public license or as
+otherwise permitted by the Creative Commons policies published at
+creativecommons.org/policies, Creative Commons does not authorize the
+use of the trademark "Creative Commons" or any other trademark or logo
+of Creative Commons without its prior written consent including,
+without limitation, in connection with any unauthorized modifications
+to any of its public licenses or any other arrangements,
+understandings, or agreements concerning use of licensed material. For
+the avoidance of doubt, this paragraph does not form part of the
+public licenses.
+
+Creative Commons may be contacted at creativecommons.org.
diff --git a/software/minizinc/docs/README.md b/software/minizinc/docs/README.md
new file mode 100644
index 0000000..ab14259
--- /dev/null
+++ b/software/minizinc/docs/README.md
@@ -0,0 +1,27 @@
+# README #
+
+This directory contains the MiniZinc documentation.
+
+### Building the docs ###
+
+You need the following tools to build the documentation:
+
+* Python 3
+* GNU make
+* Sphinx version 1.8.0. Install it using the command
+ `pip install git+https://github.com/sphinx-doc/sphinx`
+* Sphinx Read The Docs html theme. Install it using the command
+ `pip install sphinx_rtd_theme`
+* If you want to build the PDF documentation, you also need a LaTeX
+ distribution that includes xetex, and install the following fonts: Charter,
+ Lato and Inconsolata.
+
+To build the HTML documentation, simply run `make html`. To build the PDF, run `make latexpdf`.
+
+### Including the MiniZinc library reference documentation ###
+
+The reference documentation for the MiniZinc library can be generated
+automatically from the source code. Then run the following command:
+
+``mzn2doc --rst-output --include-stdlib --output-base en ../share/minizinc/std/globals.mzn``
+
diff --git a/software/minizinc/docs/chi/Makefile b/software/minizinc/docs/chi/Makefile
new file mode 100644
index 0000000..a156347
--- /dev/null
+++ b/software/minizinc/docs/chi/Makefile
@@ -0,0 +1,225 @@
+# Makefile for Sphinx documentation
+#
+
+# You can set these variables from the command line.
+SPHINXOPTS =
+SPHINXBUILD = sphinx-build
+PAPER =
+BUILDDIR = _build
+
+# Internal variables.
+PAPEROPT_a4 = -D latex_paper_size=a4
+PAPEROPT_letter = -D latex_paper_size=letter
+ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) .
+# the i18n builder cannot share the environment and doctrees with the others
+I18NSPHINXOPTS = $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) .
+
+.PHONY: help
+help:
+ @echo "Please use \`make ' where is one of"
+ @echo " html to make standalone HTML files"
+ @echo " dirhtml to make HTML files named index.html in directories"
+ @echo " singlehtml to make a single large HTML file"
+ @echo " pickle to make pickle files"
+ @echo " json to make JSON files"
+ @echo " htmlhelp to make HTML files and a HTML help project"
+ @echo " qthelp to make HTML files and a qthelp project"
+ @echo " applehelp to make an Apple Help Book"
+ @echo " devhelp to make HTML files and a Devhelp project"
+ @echo " epub to make an epub"
+ @echo " epub3 to make an epub3"
+ @echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
+ @echo " latexpdf to make LaTeX files and run them through pdflatex"
+ @echo " latexpdfja to make LaTeX files and run them through platex/dvipdfmx"
+ @echo " text to make text files"
+ @echo " man to make manual pages"
+ @echo " texinfo to make Texinfo files"
+ @echo " info to make Texinfo files and run them through makeinfo"
+ @echo " gettext to make PO message catalogs"
+ @echo " changes to make an overview of all changed/added/deprecated items"
+ @echo " xml to make Docutils-native XML files"
+ @echo " pseudoxml to make pseudoxml-XML files for display purposes"
+ @echo " linkcheck to check all external links for integrity"
+ @echo " doctest to run all doctests embedded in the documentation (if enabled)"
+ @echo " coverage to run coverage check of the documentation (if enabled)"
+ @echo " dummy to check syntax errors of document sources"
+
+.PHONY: clean
+clean:
+ rm -rf $(BUILDDIR)/*
+
+.PHONY: html
+html:
+ $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/html."
+
+.PHONY: dirhtml
+dirhtml:
+ $(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml."
+
+.PHONY: singlehtml
+singlehtml:
+ $(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml
+ @echo
+ @echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml."
+
+.PHONY: pickle
+pickle:
+ $(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle
+ @echo
+ @echo "Build finished; now you can process the pickle files."
+
+.PHONY: json
+json:
+ $(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json
+ @echo
+ @echo "Build finished; now you can process the JSON files."
+
+.PHONY: htmlhelp
+htmlhelp:
+ $(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp
+ @echo
+ @echo "Build finished; now you can run HTML Help Workshop with the" \
+ ".hhp project file in $(BUILDDIR)/htmlhelp."
+
+.PHONY: qthelp
+qthelp:
+ $(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp
+ @echo
+ @echo "Build finished; now you can run "qcollectiongenerator" with the" \
+ ".qhcp project file in $(BUILDDIR)/qthelp, like this:"
+ @echo "# qcollectiongenerator $(BUILDDIR)/qthelp/MiniZinc.qhcp"
+ @echo "To view the help file:"
+ @echo "# assistant -collectionFile $(BUILDDIR)/qthelp/MiniZinc.qhc"
+
+.PHONY: applehelp
+applehelp:
+ $(SPHINXBUILD) -b applehelp $(ALLSPHINXOPTS) $(BUILDDIR)/applehelp
+ @echo
+ @echo "Build finished. The help book is in $(BUILDDIR)/applehelp."
+ @echo "N.B. You won't be able to view it unless you put it in" \
+ "~/Library/Documentation/Help or install it in your application" \
+ "bundle."
+
+.PHONY: devhelp
+devhelp:
+ $(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp
+ @echo
+ @echo "Build finished."
+ @echo "To view the help file:"
+ @echo "# mkdir -p $$HOME/.local/share/devhelp/MiniZinc"
+ @echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/MiniZinc"
+ @echo "# devhelp"
+
+.PHONY: epub
+epub:
+ $(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub
+ @echo
+ @echo "Build finished. The epub file is in $(BUILDDIR)/epub."
+
+.PHONY: epub3
+epub3:
+ $(SPHINXBUILD) -b epub3 $(ALLSPHINXOPTS) $(BUILDDIR)/epub3
+ @echo
+ @echo "Build finished. The epub3 file is in $(BUILDDIR)/epub3."
+
+.PHONY: latex
+latex:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo
+ @echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex."
+ @echo "Run \`make' in that directory to run these through (pdf)latex" \
+ "(use \`make latexpdf' here to do that automatically)."
+
+.PHONY: latexpdf
+latexpdf:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo "Running LaTeX files through pdflatex..."
+ $(MAKE) -C $(BUILDDIR)/latex all-pdf
+ @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
+
+.PHONY: latexpdfja
+latexpdfja:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo "Running LaTeX files through platex and dvipdfmx..."
+ $(MAKE) -C $(BUILDDIR)/latex all-pdf-ja
+ @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
+
+.PHONY: text
+text:
+ $(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text
+ @echo
+ @echo "Build finished. The text files are in $(BUILDDIR)/text."
+
+.PHONY: man
+man:
+ $(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man
+ @echo
+ @echo "Build finished. The manual pages are in $(BUILDDIR)/man."
+
+.PHONY: texinfo
+texinfo:
+ $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo
+ @echo
+ @echo "Build finished. The Texinfo files are in $(BUILDDIR)/texinfo."
+ @echo "Run \`make' in that directory to run these through makeinfo" \
+ "(use \`make info' here to do that automatically)."
+
+.PHONY: info
+info:
+ $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo
+ @echo "Running Texinfo files through makeinfo..."
+ make -C $(BUILDDIR)/texinfo info
+ @echo "makeinfo finished; the Info files are in $(BUILDDIR)/texinfo."
+
+.PHONY: gettext
+gettext:
+ $(SPHINXBUILD) -b gettext $(I18NSPHINXOPTS) $(BUILDDIR)/locale
+ @echo
+ @echo "Build finished. The message catalogs are in $(BUILDDIR)/locale."
+
+.PHONY: changes
+changes:
+ $(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes
+ @echo
+ @echo "The overview file is in $(BUILDDIR)/changes."
+
+.PHONY: linkcheck
+linkcheck:
+ $(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck
+ @echo
+ @echo "Link check complete; look for any errors in the above output " \
+ "or in $(BUILDDIR)/linkcheck/output.txt."
+
+.PHONY: doctest
+doctest:
+ $(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest
+ @echo "Testing of doctests in the sources finished, look at the " \
+ "results in $(BUILDDIR)/doctest/output.txt."
+
+.PHONY: coverage
+coverage:
+ $(SPHINXBUILD) -b coverage $(ALLSPHINXOPTS) $(BUILDDIR)/coverage
+ @echo "Testing of coverage in the sources finished, look at the " \
+ "results in $(BUILDDIR)/coverage/python.txt."
+
+.PHONY: xml
+xml:
+ $(SPHINXBUILD) -b xml $(ALLSPHINXOPTS) $(BUILDDIR)/xml
+ @echo
+ @echo "Build finished. The XML files are in $(BUILDDIR)/xml."
+
+.PHONY: pseudoxml
+pseudoxml:
+ $(SPHINXBUILD) -b pseudoxml $(ALLSPHINXOPTS) $(BUILDDIR)/pseudoxml
+ @echo
+ @echo "Build finished. The pseudo-XML files are in $(BUILDDIR)/pseudoxml."
+
+.PHONY: dummy
+dummy:
+ $(SPHINXBUILD) -b dummy $(ALLSPHINXOPTS) $(BUILDDIR)/dummy
+ @echo
+ @echo "Build finished. Dummy builder generates no files."
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-144x144.png b/software/minizinc/docs/chi/_static/favicon/android-icon-144x144.png
new file mode 100644
index 0000000..44919b6
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-144x144.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-192x192.png b/software/minizinc/docs/chi/_static/favicon/android-icon-192x192.png
new file mode 100644
index 0000000..11324a4
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-192x192.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-36x36.png b/software/minizinc/docs/chi/_static/favicon/android-icon-36x36.png
new file mode 100644
index 0000000..b4b0c73
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-36x36.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-48x48.png b/software/minizinc/docs/chi/_static/favicon/android-icon-48x48.png
new file mode 100644
index 0000000..2bcff63
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-48x48.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-72x72.png b/software/minizinc/docs/chi/_static/favicon/android-icon-72x72.png
new file mode 100644
index 0000000..0cc2b06
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-72x72.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/android-icon-96x96.png b/software/minizinc/docs/chi/_static/favicon/android-icon-96x96.png
new file mode 100644
index 0000000..1a0083d
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/android-icon-96x96.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-114x114.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-114x114.png
new file mode 100644
index 0000000..06c87d0
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-114x114.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-120x120.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-120x120.png
new file mode 100644
index 0000000..7683f87
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-120x120.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-144x144.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-144x144.png
new file mode 100644
index 0000000..44919b6
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-144x144.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-152x152.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-152x152.png
new file mode 100644
index 0000000..a96cbc2
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-152x152.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-180x180.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-180x180.png
new file mode 100644
index 0000000..4ce4b9b
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-180x180.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-57x57.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-57x57.png
new file mode 100644
index 0000000..f7b9f56
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-57x57.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-60x60.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-60x60.png
new file mode 100644
index 0000000..ace131f
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-60x60.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-72x72.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-72x72.png
new file mode 100644
index 0000000..0cc2b06
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-72x72.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-76x76.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-76x76.png
new file mode 100644
index 0000000..bd4c021
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-76x76.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon-precomposed.png b/software/minizinc/docs/chi/_static/favicon/apple-icon-precomposed.png
new file mode 100644
index 0000000..98d9f05
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon-precomposed.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/apple-icon.png b/software/minizinc/docs/chi/_static/favicon/apple-icon.png
new file mode 100644
index 0000000..98d9f05
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/apple-icon.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/browserconfig.xml b/software/minizinc/docs/chi/_static/favicon/browserconfig.xml
new file mode 100644
index 0000000..c554148
--- /dev/null
+++ b/software/minizinc/docs/chi/_static/favicon/browserconfig.xml
@@ -0,0 +1,2 @@
+
+#ffffff
\ No newline at end of file
diff --git a/software/minizinc/docs/chi/_static/favicon/favicon-16x16.png b/software/minizinc/docs/chi/_static/favicon/favicon-16x16.png
new file mode 100644
index 0000000..040a439
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/favicon-16x16.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/favicon-32x32.png b/software/minizinc/docs/chi/_static/favicon/favicon-32x32.png
new file mode 100644
index 0000000..b9b8497
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/favicon-32x32.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/favicon-96x96.png b/software/minizinc/docs/chi/_static/favicon/favicon-96x96.png
new file mode 100644
index 0000000..1a0083d
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/favicon-96x96.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/favicon.ico b/software/minizinc/docs/chi/_static/favicon/favicon.ico
new file mode 100644
index 0000000..156543c
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/favicon.ico differ
diff --git a/software/minizinc/docs/chi/_static/favicon/manifest.json b/software/minizinc/docs/chi/_static/favicon/manifest.json
new file mode 100644
index 0000000..013d4a6
--- /dev/null
+++ b/software/minizinc/docs/chi/_static/favicon/manifest.json
@@ -0,0 +1,41 @@
+{
+ "name": "App",
+ "icons": [
+ {
+ "src": "\/android-icon-36x36.png",
+ "sizes": "36x36",
+ "type": "image\/png",
+ "density": "0.75"
+ },
+ {
+ "src": "\/android-icon-48x48.png",
+ "sizes": "48x48",
+ "type": "image\/png",
+ "density": "1.0"
+ },
+ {
+ "src": "\/android-icon-72x72.png",
+ "sizes": "72x72",
+ "type": "image\/png",
+ "density": "1.5"
+ },
+ {
+ "src": "\/android-icon-96x96.png",
+ "sizes": "96x96",
+ "type": "image\/png",
+ "density": "2.0"
+ },
+ {
+ "src": "\/android-icon-144x144.png",
+ "sizes": "144x144",
+ "type": "image\/png",
+ "density": "3.0"
+ },
+ {
+ "src": "\/android-icon-192x192.png",
+ "sizes": "192x192",
+ "type": "image\/png",
+ "density": "4.0"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/software/minizinc/docs/chi/_static/favicon/ms-icon-144x144.png b/software/minizinc/docs/chi/_static/favicon/ms-icon-144x144.png
new file mode 100644
index 0000000..44919b6
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/ms-icon-144x144.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/ms-icon-150x150.png b/software/minizinc/docs/chi/_static/favicon/ms-icon-150x150.png
new file mode 100644
index 0000000..366db2b
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/ms-icon-150x150.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/ms-icon-310x310.png b/software/minizinc/docs/chi/_static/favicon/ms-icon-310x310.png
new file mode 100644
index 0000000..b6354b7
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/ms-icon-310x310.png differ
diff --git a/software/minizinc/docs/chi/_static/favicon/ms-icon-70x70.png b/software/minizinc/docs/chi/_static/favicon/ms-icon-70x70.png
new file mode 100644
index 0000000..59cd61b
Binary files /dev/null and b/software/minizinc/docs/chi/_static/favicon/ms-icon-70x70.png differ
diff --git a/software/minizinc/docs/chi/_static/js/doc-links.js b/software/minizinc/docs/chi/_static/js/doc-links.js
new file mode 100644
index 0000000..e62a612
--- /dev/null
+++ b/software/minizinc/docs/chi/_static/js/doc-links.js
@@ -0,0 +1,16 @@
+window.onload = function () {
+ var to_link = document.getElementsByClassName("highlight-minizinc");
+ for (var i = 0; i
+{% endblock %}
diff --git a/software/minizinc/docs/chi/_templates/layout.html b/software/minizinc/docs/chi/_templates/layout.html
new file mode 100644
index 0000000..a72e7e9
--- /dev/null
+++ b/software/minizinc/docs/chi/_templates/layout.html
@@ -0,0 +1,61 @@
+{% extends "!layout.html" %}
+{% block extrahead %}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+{% endblock %}
+{% block sidebartitle %}
+
+ {% if logo %}
+ {# Not strictly valid HTML, but it's the only way to display/scale
+ it properly, without weird scripting or heaps of work
+ #}
+
+ {% endif %}
+
+
+ {% if theme_display_version %}
+ {%- set nav_version = release %}
+ {% if nav_version %}
+
+ {{ nav_version }}
+
+ {% endif %}
+ {% endif %}
+
+ {% include "searchbox.html" %}
+{% endblock %}
+
+{% block menu %}
+ {#
+ The singlehtml builder doesn't handle this toctree call when the
+ toctree is empty. Skip building this for now.
+ #}
+ {% if 'singlehtml' not in builder %}
+ {% set global_toc = toctree(maxdepth=theme_navigation_depth|int,
+ collapse=theme_collapse_navigation|tobool,
+ includehidden=theme_includehidden|tobool,
+ titles_only=theme_titles_only|tobool) %}
+ {% endif %}
+ {{ project }}
+ {% if global_toc %}
+ {{ global_toc }}
+ {% else %}
+
+
{{ toc }}
+ {% endif %}
+ {% endblock %}
\ No newline at end of file
diff --git a/software/minizinc/docs/chi/api_interfacing.rst b/software/minizinc/docs/chi/api_interfacing.rst
new file mode 100644
index 0000000..dbaf98c
--- /dev/null
+++ b/software/minizinc/docs/chi/api_interfacing.rst
@@ -0,0 +1 @@
+.. include:: ../en/api_interfacing.rst
diff --git a/software/minizinc/docs/chi/basic_steps.rst b/software/minizinc/docs/chi/basic_steps.rst
new file mode 100644
index 0000000..aa03010
--- /dev/null
+++ b/software/minizinc/docs/chi/basic_steps.rst
@@ -0,0 +1 @@
+.. include:: ../en/basic_steps.rst
diff --git a/software/minizinc/docs/chi/command_line.rst b/software/minizinc/docs/chi/command_line.rst
new file mode 100644
index 0000000..8b35eb4
--- /dev/null
+++ b/software/minizinc/docs/chi/command_line.rst
@@ -0,0 +1 @@
+.. include:: ../en/command_line.rst
diff --git a/software/minizinc/docs/chi/conf.py b/software/minizinc/docs/chi/conf.py
new file mode 100755
index 0000000..787bdb0
--- /dev/null
+++ b/software/minizinc/docs/chi/conf.py
@@ -0,0 +1,479 @@
+#!/usr/bin/env python3
+# -*- coding: utf-8 -*-
+#
+# MiniZinc documentation build configuration file, created by
+# sphinx-quickstart on Sat Nov 26 18:22:59 2016.
+#
+# This file is execfile()d with the current directory set to its
+# containing dir.
+#
+# Note that not all possible configuration values are present in this
+# autogenerated file.
+#
+# All configuration values have a default; values that are commented out
+# serve to show the default.
+
+# If extensions (or modules to document with autodoc) are in another directory,
+# add these directories to sys.path here. If the directory is relative to the
+# documentation root, use os.path.abspath to make it absolute, like shown here.
+#
+import os
+import sys
+sys.path.insert(0, os.path.abspath('../utils'))
+
+# -- General configuration ------------------------------------------------
+
+# If your documentation needs a minimal Sphinx version, state it here.
+#
+# needs_sphinx = '1.0'
+
+import defblock
+import inlinesyntaxhighlight
+
+# Add any Sphinx extension module names here, as strings. They can be
+# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom
+# ones.
+extensions = [
+ 'sphinx.ext.todo',
+ 'sphinx.ext.mathjax',
+ 'defblock',
+ 'inlinesyntaxhighlight',
+ 'sphinxtogithub'
+]
+
+inline_highlight_respect_highlight = False
+
+inline_highlight_literals = False
+
+# Add any paths that contain templates here, relative to this directory.
+templates_path = ['_templates']
+
+# The suffix(es) of source filenames.
+# You can specify multiple suffix as a list of string:
+#
+# source_suffix = ['.rst', '.md']
+source_suffix = '.rst'
+
+# The encoding of source files.
+#
+# source_encoding = 'utf-8-sig'
+
+# The master toctree document.
+master_doc = 'index'
+
+# General information about the project.
+project = 'The MiniZinc Handbook'
+copyright = '2016, 2017, 2018, 2019, 2020 Peter J. Stuckey, Kim Marriott, Guido Tack'
+author = 'Peter J. Stuckey, Kim Marriott, Guido Tack'
+
+# The version info for the project you're documenting, acts as replacement for
+# |version| and |release|, also used in various other places throughout the
+# built documents.
+#
+# The short X.Y version.
+version = '2.5'
+# The full version, including alpha/beta/rc tags.
+release = '2.5.5'
+
+# The language for content autogenerated by Sphinx. Refer to documentation
+# for a list of supported languages.
+#
+# This is also used if you do content translation via gettext catalogs.
+# Usually you set "language" from the command line for these cases.
+language = None
+
+# There are two options for replacing |today|: either, you set today to some
+# non-false value, then it is used:
+#
+# today = ''
+#
+# Else, today_fmt is used as the format for a strftime call.
+#
+# today_fmt = '%B %d, %Y'
+
+# List of patterns, relative to source directory, that match files and
+# directories to ignore when looking for source files.
+# This patterns also effect to html_static_path and html_extra_path
+exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store', 'api_interfacing.rst']
+
+# The reST default role (used for this markup: `text`) to use for all
+# documents.
+#
+# default_role = None
+
+# If true, '()' will be appended to :func: etc. cross-reference text.
+#
+# add_function_parentheses = True
+
+# If true, the current module name will be prepended to all description
+# unit titles (such as .. function::).
+#
+# add_module_names = True
+
+# If true, sectionauthor and moduleauthor directives will be shown in the
+# output. They are ignored by default.
+#
+# show_authors = False
+
+# The name of the Pygments (syntax highlighting) style to use.
+pygments_style = 'manni'
+
+# A list of ignored prefixes for module index sorting.
+# modindex_common_prefix = []
+
+# If true, keep warnings as "system message" paragraphs in the built documents.
+# keep_warnings = False
+
+# If true, `todo` and `todoList` produce output, else they produce nothing.
+todo_include_todos = True
+
+
+# -- Options for HTML output ----------------------------------------------
+
+import sphinx_rtd_theme
+
+# The theme to use for HTML and HTML Help pages. See the documentation for
+# a list of builtin themes.
+#
+# html_theme = 'alabaster'
+
+html_theme = 'sphinx_rtd_theme'
+html_theme_path = ["_themes", ]
+# html_theme_path = sphinx_bootstrap_theme.get_html_theme_path()
+
+# Theme options are theme-specific and customize the look and feel of a theme
+# further. For a list of options available for each theme, see the
+# documentation.
+#
+html_theme_options = {
+ 'logo_only' : False,
+ 'canonical_url' : 'http://www.minizinc.org/doc-latest/en/'
+}
+
+# Add any paths that contain custom themes here, relative to this directory.
+# html_theme_path = []
+
+# The name for this set of Sphinx documents.
+# " v documentation" by default.
+#
+html_title = project+" "+release
+
+# A shorter title for the navigation bar. Default is the same as html_title.
+#
+# html_short_title = None
+
+# The name of an image file (relative to this directory) to place at the top
+# of the sidebar.
+#
+html_logo = 'figures/MiniZn_logo_2.svg'
+
+# The name of an image file (relative to this directory) to use as a favicon of
+# the docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32
+# pixels large.
+#
+# html_favicon = None
+
+# Add any paths that contain custom static files (such as style sheets) here,
+# relative to this directory. They are copied after the builtin static files,
+# so a file named "default.css" will overwrite the builtin "default.css".
+html_static_path = ['_static']
+
+html_js_files = ['js/doc-links.js']
+
+# Add any extra paths that contain custom files (such as robots.txt or
+# .htaccess) here, relative to this directory. These files are copied
+# directly to the root of the documentation.
+#
+# html_extra_path = []
+
+# If not None, a 'Last updated on:' timestamp is inserted at every page
+# bottom, using the given strftime format.
+# The empty string is equivalent to '%b %d, %Y'.
+#
+# html_last_updated_fmt = None
+
+# If true, SmartyPants will be used to convert quotes and dashes to
+# typographically correct entities.
+#
+# html_use_smartypants = True
+
+# Custom sidebar templates, maps document names to template names.
+#
+# html_sidebars = {}
+
+# Additional templates that should be rendered to pages, maps page names to
+# template names.
+#
+# html_additional_pages = {}
+
+# If false, no module index is generated.
+#
+# html_domain_indices = True
+
+# If false, no index is generated.
+#
+# html_use_index = True
+
+# If true, the index is split into individual pages for each letter.
+#
+html_split_index = False
+
+# If true, links to the reST sources are added to the pages.
+#
+html_show_sourcelink = False
+html_copy_source = False
+
+# If true, "Created using Sphinx" is shown in the HTML footer. Default is True.
+#
+html_show_sphinx = False
+
+# If true, "(C) Copyright ..." is shown in the HTML footer. Default is True.
+#
+# html_show_copyright = True
+
+# If true, an OpenSearch description file will be output, and all pages will
+# contain a tag referring to it. The value of this option must be the
+# base URL from which the finished HTML is served.
+#
+# html_use_opensearch = ''
+
+# This is the file name suffix for HTML files (e.g. ".xhtml").
+# html_file_suffix = None
+
+# Language to be used for generating the HTML full-text search index.
+# Sphinx supports the following languages:
+# 'da', 'de', 'en', 'es', 'fi', 'fr', 'h', 'it', 'ja'
+# 'nl', 'no', 'pt', 'ro', 'r', 'sv', 'tr', 'zh'
+#
+# html_search_language = 'en'
+
+# A dictionary with options for the search language support, empty by default.
+# 'ja' uses this config value.
+# 'zh' user can custom change `jieba` dictionary path.
+#
+# html_search_options = {'type': 'default'}
+
+# The name of a javascript file (relative to the configuration directory) that
+# implements a search results scorer. If empty, the default will be used.
+#
+# html_search_scorer = 'scorer.js'
+
+# Output file base name for HTML help builder.
+htmlhelp_basename = 'MiniZincdoc'
+
+# -- Options for LaTeX output ---------------------------------------------
+
+latex_engine = 'xelatex'
+
+latex_elements = {
+ # The paper size ('letterpaper' or 'a4paper').
+ #
+ 'papersize': 'a4paper',
+'fontpkg': r'''
+\usepackage{fontspec}
+\setmainfont{Charter}
+\setsansfont{Lato}
+\setmonofont{Inconsolata}
+\usepackage{ctex}
+''',
+ # The font size ('10pt', '11pt' or '12pt').
+ #
+ 'pointsize': '11pt',
+
+ # Additional stuff for the LaTeX preamble.
+ #
+ # 'preamble': '',
+ 'preamble': r'\usepackage{../../../utils/mznstyle}',
+ # Latex figure (float) alignment
+ #
+ # 'figure_align': 'htbp',
+ 'fncychap': r'\usepackage[Sonny]{fncychap}',
+}
+
+# Grouping the document tree into LaTeX files. List of tuples
+# (source start file, target name, title,
+# author, documentclass [howto, manual, or own class]).
+latex_documents = [
+ (master_doc, 'MiniZinc.tex', 'MiniZinc Handbook',
+ 'Peter J. Stuckey, Kim Marriott, Guido Tack', 'manual'),
+]
+
+# The name of an image file (relative to this directory) to place at the top of
+# the title page.
+#
+latex_logo = 'figures/MiniZn_logo_2_small.pdf'
+
+# For "manual" documents, if this is true, then toplevel headings are parts,
+# not chapters.
+#
+latex_toplevel_sectioning = "part"
+
+# If true, show page references after internal links.
+#
+latex_show_pagerefs = True
+
+# If true, show URL addresses after external links.
+#
+latex_show_urls = "footnote"
+
+# Documents to append as an appendix to all manuals.
+#
+# latex_appendices = []
+
+# It false, will not define \strong, \code, itleref, \crossref ... but only
+# \sphinxstrong, ..., \sphinxtitleref, ... To help avoid clash with user added
+# packages.
+#
+# latex_keep_old_macro_names = True
+
+# If false, no module index is generated.
+#
+# latex_domain_indices = True
+
+
+# -- Options for manual page output ---------------------------------------
+
+# One entry per manual page. List of tuples
+# (source start file, name, description, authors, manual section).
+man_pages = [
+ (master_doc, 'minizinc', 'MiniZinc Documentation',
+ [author], 1)
+]
+
+# If true, show URL addresses after external links.
+#
+# man_show_urls = False
+
+
+# -- Options for Texinfo output -------------------------------------------
+
+# Grouping the document tree into Texinfo files. List of tuples
+# (source start file, target name, title, author,
+# dir menu entry, description, category)
+texinfo_documents = [
+ (master_doc, 'MiniZinc', 'MiniZinc Documentation',
+ author, 'MiniZinc', 'One line description of project.',
+ 'Miscellaneous'),
+]
+
+# Documents to append as an appendix to all manuals.
+#
+# texinfo_appendices = []
+
+# If false, no module index is generated.
+#
+# texinfo_domain_indices = True
+
+# How to display URL addresses: 'footnote', 'no', or 'inline'.
+#
+# texinfo_show_urls = 'footnote'
+
+# If true, do not generate a @detailmenu in the "Top" node's menu.
+#
+# texinfo_no_detailmenu = False
+
+
+# -- Options for Epub output ----------------------------------------------
+
+# Bibliographic Dublin Core info.
+epub_title = project
+epub_author = author
+epub_publisher = author
+epub_copyright = copyright
+
+# The basename for the epub file. It defaults to the project name.
+# epub_basename = project
+
+# The HTML theme for the epub output. Since the default themes are not
+# optimized for small screen space, using the same theme for HTML and epub
+# output is usually not wise. This defaults to 'epub', a theme designed to save
+# visual space.
+#
+# epub_theme = 'epub'
+
+# The language of the text. It defaults to the language option
+# or 'en' if the language is not set.
+#
+# epub_language = ''
+
+# The scheme of the identifier. Typical schemes are ISBN or URL.
+# epub_scheme = ''
+
+# The unique identifier of the text. This can be a ISBN number
+# or the project homepage.
+#
+# epub_identifier = ''
+
+# A unique identification for the text.
+#
+# epub_uid = ''
+
+# A tuple containing the cover image and cover page html template filenames.
+#
+# epub_cover = ()
+
+# A sequence of (type, uri, title) tuples for the guide element of content.opf.
+#
+# epub_guide = ()
+
+# HTML files that should be inserted before the pages created by sphinx.
+# The format is a list of tuples containing the path and title.
+#
+# epub_pre_files = []
+
+# HTML files that should be inserted after the pages created by sphinx.
+# The format is a list of tuples containing the path and title.
+#
+# epub_post_files = []
+
+# A list of files that should not be packed into the epub file.
+epub_exclude_files = ['search.html']
+
+# The depth of the table of contents in toc.ncx.
+#
+# epub_tocdepth = 3
+
+# Allow duplicate toc entries.
+#
+# epub_tocdup = True
+
+# Choose between 'default' and 'includehidden'.
+#
+# epub_tocscope = 'default'
+
+# Fix unsupported image types using the Pillow.
+#
+# epub_fix_images = False
+
+# Scale large images.
+#
+# epub_max_image_width = 0
+
+# How to display URL addresses: 'footnote', 'no', or 'inline'.
+#
+# epub_show_urls = 'inline'
+
+# If false, no index is generated.
+#
+# epub_use_index = True
+
+numfig = True
+numfig_secnum_depth = 2
+
+rst_prolog = """
+.. role:: mzn(code)
+ :language: minizinc
+
+.. role:: mzndef(code)
+ :language: minizincdef
+"""
+
+sphinx_to_github = True
+sphinx_to_github_verbose = True
+sphinx_to_github_encoding = "utf-8"
+
+def setup(sphinx):
+ from minizinc_lexer import MznLexer, MznDefLexer
+ sphinx.add_lexer("minizinc", MznLexer())
+ sphinx.add_lexer("minizincdef", MznDefLexer())
+ sphinx.add_stylesheet("style.css")
diff --git a/software/minizinc/docs/chi/efficient.rst b/software/minizinc/docs/chi/efficient.rst
new file mode 100644
index 0000000..086e656
--- /dev/null
+++ b/software/minizinc/docs/chi/efficient.rst
@@ -0,0 +1,346 @@
+.. _sec-efficient:
+
+MiniZinc中的有效建模实践
+=========================================
+
+对同一个问题,几乎总是存在多种方式来建模。其中一些产生的模型可以很有效地求解,另外一些则不是。通常情况下,我们很难提前判断哪个模型是对解决一个特定的问题最有效的。事实上,这或许十分依赖于我们使用的底层求解器。在这一章中,我们专注于建模实践,来避免产生模型的过程和产生的模型低效。
+
+变量界限
+---------------
+
+.. index::
+ single: variable; bound
+
+有限域传播器,是MiniZinc所针对的求解器中的核心类型。在当其所涉及到的变量的界限越紧凑时,此传播器越有效。
+它也会当问题含有会取很大整型数值的子表达式时表现得很差,因为它们可能会隐式地限制整型变量的大小。
+
+
+.. literalinclude:: examples/grocery.mzn
+ :language: minizinc
+ :name: ex-grocery
+ :caption: 没有无界整数的模型 (:download:`grocery.mzn `).
+
+在 :numref:`ex-grocery` 中的中的杂货店问题要找寻4个物品使得它们的价格加起来有7.11元并且乘起来也有7.11元。变量被声明为无界限。运行
+
+.. code-block:: bash
+
+ $ minizinc --solver g12fd grocery.mzn
+
+得到
+
+.. code-block:: none
+
+ =====UNSATISFIABLE=====
+ % /tmp/mznfile85EWzj.fzn:11: warning: model inconsistency detected before search.
+
+这是因为乘法中的中间表达式的类型也会是 :mzn:`var int` ,也会被求解器给一个默认的界限 :math:`-1,000,000 \dots 1,000,000` 。但是这个范围太小了以至于不能承载住中间表达式所可能取的值。
+
+更改模型使得初始变量都被声明为拥有更紧致的界限
+
+.. code-block:: minizinc
+
+ var 1..711: item1;
+ var 1..711: item2;
+ var 1..711: item3;
+ var 1..711: item4;
+
+我们得到一个更好的模型,因为现在MiniZinc可以推断出中间表达式的界限,并且使用此界限而不是默认的界限。在做此更改后,求解模型我们得到
+
+.. code-block:: none
+
+ {120,125,150,316}
+ ----------
+
+注意,就算是改善的模型也可能对于某些求解器来说会很难解决。
+运行
+
+.. code-block:: bash
+
+ $ minizinc --solver g12lazy grocery.mzn
+
+不能得到任何结果,因为求解器给中间产生的变量创建了巨大的表示。
+
+.. defblock:: 给变量加界限
+
+ .. index::
+ single: variable; bound
+
+ 在模型中要尽量使用有界限的变量。当使用 :mzn:`let` 声明来引进新的变量时,始终尽量给它们定义正确的和紧凑的界限。这会使得你的模型更有效率,避免出现意外溢出的可能性。
+ 一个例外是当你引进一个新的变量然后立刻定义它等于一个表达式,通常MiniZinc都可以从此表达式推断出此变量有效的界限。
+
+有效的生成元
+--------------------
+
+.. index::
+ single: generator
+
+想象下我们想要计算在一个图中出现的三角形的个数( :math:`K_3` 子图)。
+假设此图由一个邻接矩阵定义:如果点$i$和$j$邻接,则 :mzn:`adj[i,j]` 为真。
+我们或许可以写成
+
+.. code-block:: minizinc
+
+ int: count = sum ([ 1 | i,j,k in NODES where i < j /\ j < k
+ /\ adj[i,j] /\ adj[i,k] /\ adj[j,k]]);
+
+这当然是对的,但是它检查了所有点可能组成的三元组。
+如果此图是稀疏的,在意识到一旦我们选择了 :mzn:`i` 和 :mzn:`j` ,就可以进行一些测试之后,我们可以做得更好。
+
+.. code-block:: minizinc
+
+ int: count = sum ([ 1 | i,j in NODES where i < j /\ adj[i,j],
+ k in NODES where j < k /\ adj[i,k] /\ adj[j,k]]);
+
+你可以使用内建 :mzn:`trace` :index:`函数 ` 来帮助决定在生成元内发生了什么。
+
+.. defblock:: 追踪
+
+ 函数 :mzn:`trace(s,e)` 在对表达式 :mzn:`e` 求值并返回它的值之前就输出字符串 :mzn:`s` 。它可以在任何情境下使用。
+
+例如,我们可以查看在两种计算方式下的内部循环中分别进行了多少次测试。
+
+.. literalinclude:: examples/count1.mzn
+ :language: minizinc
+ :lines: 8-15
+
+得到输出:
+
+.. code-block:: none
+
+ ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+ ----------
+
+表示内部循环进行了64次,而
+
+.. literalinclude:: examples/count2.mzn
+ :language: minizinc
+ :lines: 13-14
+
+得到输出
+
+.. code-block:: none
+
+ ++++++++++++++++
+ ----------
+
+表示内部循环进行了16次。
+
+注意你可以在 :mzn:`trace` 中使用单独的字符串来帮助你理解模型创建过程中发生了什么。
+
+.. literalinclude:: examples/count3.mzn
+ :language: minizinc
+ :lines: 13-15
+
+会输出在计算过程中找到的每个三角形。得到输出
+
+.. code-block:: none
+
+ (1,2,3)
+ ----------
+
+我们要承认这里我们有一点点作弊: 在某些情况下, MiniZinc编译器实际上会把 ``where`` 从句中的参数自动重新排序, 所以他们会尽快地被计算。在这种情况下, 加入 ``trace`` 函数实际上 *阻止* 了这种优化. 一般来说, 通过分离 ``where`` 从句把它们摆到尽量接近生成元, 这其实是一个很好的主意来帮助编译器运作正常。
+
+
+冗余约束
+---------------------
+
+.. index::
+ single: constraint; redundant
+
+模型的形式会影响约束求解器求解它的效率。
+在很多情况下加入冗余约束,即被现有的模型逻辑上隐含的约束,可能会让求解器在更早时候产生更多可用的信息从而提高找寻解的搜索效率。
+
+回顾下第 :ref:`sec-complex` 节中的魔术串问题。
+
+运行 :mzn:`n = 16` 时的模型:
+
+.. code-block:: bash
+
+ $ minizinc --all-solutions --statistics magic-series.mzn -D "n=16;"
+
+:mzn:`n = 16`
+
+.. code-block:: none
+
+ s = [12, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0];
+ ----------
+ ==========
+
+统计数据显示需要有89个失败。
+
+我们可以在模型中加入冗余约束。由于序列中的每个数字是用来计算某一个数字出现的次数,我们知道它们的和肯定是 :mzn:`n` 。
+类似地,由于这个序列是魔术的,我们知道 :mzn:`s[i] * i` 的和肯定也是 :mzn:`n` 。
+使用如下方式把这些约束加入我们的模型 :numref:`ex-magic-series2`.
+
+.. literalinclude:: examples/magic-series2.mzn
+ :language: minizinc
+ :name: ex-magic-series2
+ :caption: 使用冗余约束求解魔术串问题模型 (:download:`magic-series2.mzn `).
+
+像之前那样求解同一个问题
+
+.. code-block:: bash
+
+ $ minizinc --all-solutions --statistics magic-series2.mzn -D "n=16;"
+
+产生了同样的输出。但是统计显示只搜索了13个决策点。这些冗余约束使得求解器更早地去剪枝。
+
+
+模型选择
+-----------------
+
+在MiniZinc中有很多方式去给同一个问题建模,尽管其中有些模型或许会比另外的一些模型更自然。
+不同的模型或许会产生不同的求解效率。更糟糕的是,在不同的求解后端中,不同的模型或许会更好或更差。
+但是,我们还是可以给出一些关于普遍情况下产生更好的模型的指导:
+
+.. defblock:: 模型之间的选择
+
+ 一个好的模型倾向于有以下特征
+
+ - 更少量的变量,或者至少是更少量的没有被其他变量功能上定义的变量。
+ - 更小的变量定义域范围
+ - 模型的约束定义更简洁或者直接
+ - 尽可能地使用全局约束
+
+ 实际情况中,所有这些都需要通过检查这个模型的搜索到底多有效率来断定模型好坏。通常除了用实验之外,我们很难判断搜索是否高效。
+
+观察如下问题,我们要找寻1到 :math:`n` 这 :math:`n` 个数字的排列,使得相邻数字的差值也形成一个1到 :math:`n` 的排列。
+:numref:`ex-allint` 中给出了一个用直观的方式来建模此问题的模型。注意变量 :mzn:`u` 被变量 :mzn:`x` 功能性定义。所以最差情况下的搜索空间是 :math:`n^n`。
+
+.. literalinclude:: examples/allinterval.mzn
+ :language: minizinc
+ :name: ex-allint
+ :caption: 对于CSPlib ``prob007`` 所有间隔系列问题的模型 (:download:`allinterval.mzn `).
+
+在这个模型中,数组 :mzn:`x` 代表 :mzn:`n` 个数字的排序。约束自然地可用 :mzn:`alldifferent` 来表示。
+
+求解模型
+
+.. code-block:: bash
+
+ $ minizinc --solver g12fd --all-solutions --statistics allinterval.mzn -D "n=10;"
+
+在84598个决策点和3秒的时间内找到了所有的解。
+
+另外一个模型是使用数组 :mzn:`y` ,其中 :mzn:`y[i]` 代表数字 :mzn:`i` 在序列中的位置。
+我们同时也使用变量 :mzn:`v` 来建模表示差的位置。 :mzn:`v[i]` 表示了绝对值差 :mzn:`i` 在序列出现的位置。
+如果 :mzn:`y[i]` 和 :mzn:`y[j]` 差别为一,其中 :mzn:`j > i` ,则代表了它们的位置是相邻的。所以 :mzn:`v[j-i]` 被约束为两个位置中最早的那个。
+我们可以给这个模型加入两个冗余约束:由于我们知道差值 :mzn:`n-1` 肯定会产生,我们就可以推断出1和 :mzn:`n` 的位置必须是相邻的 :mzn:`abs( y[1] - y[n] ) = 1` 。同时也告诉我们差值 :mzn:`n-1` 的位置就是在 :mzn:`y[1]` 和 :mzn:`y[n]` 中的最早的那个位置,即 :mzn:`v[n-1] = min(y[1], y[n])` 。有了这些之后,我们可以建模此问题为:numref:`ex-allint2` 。
+输出语句从位置数组 :mzn:`y` 里重现了原本的序列 :mzn:`x` 。
+
+.. literalinclude:: examples/allinterval2.mzn
+ :language: minizinc
+ :name: ex-allint2
+ :caption: CSPlib中全区间序列问题 ``prob007`` 的一个逆向模型。 (:download:`allinterval2.mzn `).
+
+逆向模型跟初始模型有同样的变量和定义域大小。但是相对于给变量 :mzn:`x` 和 :mzn:`u` 的关系建模,逆向模型使用了一个更加非直接的方式来给变量 :mzn:`y` 和 :mzn:`v` 的关系建模。所以我们或许期望初始模型更好些。
+
+命令
+
+.. code-block:: bash
+
+ $ minizinc --solver g12fd --all-solutions --statistics allinterval2.mzn -D "n=10;"
+
+在75536个决策点和18秒内找到了所有的解。
+有趣的是,尽管这个模型不是简洁的,在变量 :mzn:`y` 上搜索比在变量 :mzn:`x` 上搜索更加有效率。
+简洁的缺乏意味着尽管搜索需要更少的决策点,但是在时间上实质上会更慢。
+
+.. _sec-multiple-modelling-and-channels:
+
+多重建模和连通
+-------------------------------
+
+当我们对同一个问题有两个模型时,由于每个模型可以给求解器不同的信息,通过把两个模型中的变量系到一起从而同时使用两个模型或许对我们是有帮助的。
+
+.. literalinclude:: examples/allinterval3.mzn
+ :language: minizinc
+ :name: ex-allint3
+ :caption: CSPlib中全区间序列问题 ``prob007`` 的一个双重模型。 (:download:`allinterval3.mzn `).
+
+:numref:`ex-allint3` 给出了一个结合 :download:`allinterval.mzn ` 和 :download:`allinterval2.mzn ` 特征的双重模型。
+模型的开始来自于 :download:`allinterval.mzn ` 。我们接着介绍了来自于 :download:`allinterval2.mzn ` 中的变量 :mzn:`y` 和 :mzn:`v` 。我们使用全局约束 :mzn:`inverse` 来把变量绑到一起: :mzn:`inverse(x,y)` 约束 :mzn:`y` 为 :mzn:`x` 的逆向函数(反之亦然),即, :mzn:`x[i] = j <-> y[j] = i` 。 :numref:`ex-inverse` 中给出了它的一个定义。这个模型没有包含把变量 :mzn:`y` 和 :mzn:`v` 关联起来的约束,它们是冗余的(实际上是传播冗余)。所以它们不会给基于传播的求解器多余的信息。 :mzn:`alldifferent` 也不见了。原因是它们被逆向约束变得冗余了(传播冗余)。
+唯一的约束是关于变量 :mzn:`x` 和 :mzn:`u` 和关系的约束以及 :mzn:`y` 和 :mzn:`v` 的冗余约束。
+
+.. literalinclude:: examples/inverse.mzn
+ :language: minizinc
+ :name: ex-inverse
+ :caption: 全局约束 ``inverse`` 的一个定义 (:download:`inverse.mzn `).
+
+双重模型的一个优点是我们可以有更多的定义不同搜索策略的视角。运行双重模型,
+
+.. code-block:: bash
+
+ $ minizinc --solver g12fd --all-solutions --statistics allinterval3.mzn -D "n=10;"
+
+注意它使用逆向模型的搜索策略,标记变量 :mzn:`y` ,在1714决策点和0.5秒内找到了所有的解。注意标记变量 :mzn:`x` 来运行同样的模型,需要13142个决策点和1.5秒。
+
+对称
+--------
+
+对称在约束满足和优化问题中是常见的。我们可以再次通过 :numref:`ex-queens` 来看一下这个问题。在 :numref:`fig-queens-sym` 棋盘的左上方展示了一个8皇后问题的解(标记为 "original")。剩下的棋盘展示了7个解的对称版本:旋转90度,180度和270度,还有垂直翻转。
+
+.. _fig-queens-sym:
+
+.. figure:: figures/queens_symm.*
+
+ 8皇后问题解的对称变化
+
+如果我们想要穷举8皇后问题的 *所有* 解,很明显我们需要通过穷举 *彼此之间不对称的* 解 为求解器省下一些工作,然后生成这些的对称版本。这是我们想要在约束模型中摆脱对称的一个理由。另外一个更重要的理由是,我们的求解器也可能会 **探索非解状态的对称版本!**
+
+举个例子,一个典型的约束求解器可能会尝试把第1列皇后放在第1行上(这是可以的),然后尝试把第2列的皇后放到第3行上。 这在第一眼看是没有违反任何约束的。然而,这种设置不能被完成成为一个解(求解器会在一些搜索之后发现这一点). :numref:`fig-queens-sym-unsat` 在左上方的棋盘展示了这种设置。现在没有任何东西会阻止求解器去尝试,比如,在 :numref:`fig-queens-sym-unsat` 最低一行的左边第二种设置。其中第1列的皇后仍然在第1行,而第3列的皇后放在第2行。于是,即便是搜索一个解,求解器可能需要探索很多它已经看到并证明不可满足状态的对称状态!
+
+.. _fig-queens-sym-unsat:
+
+.. figure:: figures/queens_symm_unsat.*
+
+ 8皇后问题不可满足约束的部分解的对称版本
+
+静态的对称性破缺
+~~~~~~~~~~~~~~~~~~~~~~~~
+
+解决对称问题的建模技巧叫做 *对称性破缺* , 在它的最简单形式里, 需要在模型中加入约束使一个(不完整的)赋值的所有对称变换去除掉而保留一个。 这些约束称作 *静态的对称性破缺约束* 。
+
+对称性破缺背后基本的想法是加入 *顺序* 。举个例子, 我们可以通过简单地加入约束使第一列的皇后必须在棋盘的上半部分,从而去除掉所有棋盘垂直翻转的。
+
+.. code-block:: minizinc
+
+ constraint q[1] <= n div 2;
+
+请相信以上约束会去除掉在 :numref:`fig-queens-sym` 中所有对称变换的一半。 为了去除 *所有* 对称,我们需要更多工作。
+
+当我们把所有对称都表示成数组变量的排列,一组 *字典顺序约束* 可以用于破坏所有对称。 举个例子,如果数组变量名为 :mzn:`x` ,而翻转数组是这个问题的一种对称,那么以下约束可以破坏那种对称:
+
+.. code-block:: minizinc
+
+ constraint lex_lesseq(x, reverse(x));
+
+那么二维数组又怎么样呢?字典顺序同样适用,我们只需要把数组转换成一维的. 举个例子,下面的约束破坏了沿着其中一个对角线翻转数组的对称性(注意到第二个生成式里对换的数组下标):
+
+.. code-block:: minizinc
+
+ array[1..n,1..n] of var int: x;
+ constraint lex_lesseq([ x[i,j] | i,j in 1..n ], [ x[j,i] | i,j in 1..n ]);
+
+字典排序约束的好处在于我们可以加入多个(同时破坏几个对称性),而不需要它们互相干扰,只要我们保持第一个参数中的顺序一致即可。
+
+对于n皇后问题,很不幸的是这个技巧不能马上适用, 因为又一些对称不能被描述成数组 :mzn:`q` 的排列。 克服这个问题的技巧是把n皇后问题表示成布尔变量。 对于每个棋盘的每个格子, 布尔变量表示是否有一个皇后在上面。现在所有的对称性都可以表示成这个数组的排列。 因为主要的n皇后问题的主要约束在整型数组 :mzn:`q` 里面更加容易表达, 我们只需要两个模型都用起来,然后在它们之间加入连通约束。 正如 :ref:`sec-multiple-modelling-and-channels` 中解释的一样。
+
+加入布尔变量,连通约束和对称性破缺约束的完整模型展示在 :numref:`ex-queens-sym` 里面。 我们可以做一些小实验来检查它是否成功的破坏所有对称性。 尝试用不断增加的 :mzn:`n` 运行模型, 比如从1到10, 数一下解的个数(比如,使用 Gecode求解器的 ``-s`` 标志, 或者选择IDE中"Print all solutions"和"Statistics for solving")。 你应该可以获得以下数列的解: 1, 0, 0, 1, 2, 1, 6, 12, 46, 92。 你可以搜索 *On-Line Encyclopedia of Integer Sequences* (http://oeis.org) 来校验这个序列。
+
+.. literalinclude:: examples/nqueens_sym.mzn
+ :language: minizinc
+ :name: ex-queens-sym
+ :start-after: % 可选的
+ :end-before: % 搜索
+ :caption: n皇后问题对称性破缺的部分模型 (full model: :download:`nqueens_sym.mzn `).
+
+
+其他对称的例子
+~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+许多其他问题都有内在的对称性,破坏这些对称性常常会令求解表现不一样。以下是一些常见的例子:
+
+- 装箱问题: 当尝试把物品装入箱子时,任意两个有相同容量的箱子都是对称的
+- 涂色问题: 当尝试为一个图涂色使得所有相邻的节点都有不同的颜色时,我们通常用整型变量对颜色建模。但是,对颜色的任意排列都是一种合法的涂色方案。
+- 车辆路线问题: 如果任务是给顾客分配一些车辆,任何两辆有相同容量的车可能是对称的(这跟装箱问题是相似的)
+- 排班/时间表问题: 两个有相同能力的职员可能是可以相互交换的,就像两个有相同容量或者设备的的房间一样
diff --git a/software/minizinc/docs/chi/examples/allinterval.mzn b/software/minizinc/docs/chi/examples/allinterval.mzn
new file mode 100644
index 0000000..2995051
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/allinterval.mzn
@@ -0,0 +1,14 @@
+include "alldifferent.mzn";
+
+int: n;
+
+array[1..n] of var 1..n: x; % 数字的序列
+array[1..n-1] of var 1..n-1: u; % 差的序列
+
+constraint alldifferent(x);
+constraint alldifferent(u);
+constraint forall(i in 1..n-1)(u[i] = abs(x[i+1] - x[i]));
+
+solve :: int_search(x, first_fail, indomain_min, complete)
+ satisfy;
+output ["x = ",show(x),"\n"];
diff --git a/software/minizinc/docs/chi/examples/allinterval2.mzn b/software/minizinc/docs/chi/examples/allinterval2.mzn
new file mode 100644
index 0000000..3cbf731
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/allinterval2.mzn
@@ -0,0 +1,22 @@
+include "alldifferent.mzn";
+
+int: n;
+
+array[1..n] of var 1..n: y; % 每个数值的位置
+array[1..n-1] of var 1..n-1: v; % 差值i的位置
+
+constraint alldifferent(y);
+constraint alldifferent(v);
+constraint forall(i,j in 1..n where i < j)(
+ (y[i] - y[j] = 1 -> v[j-i] = y[j]) /\
+ (y[j] - y[i] = 1 -> v[j-i] = y[i])
+ );
+
+constraint abs(y[1] - y[n]) = 1 /\ v[n-1] = min(y[1], y[n]);
+
+solve :: int_search(y, first_fail, indomain_min, complete)
+ satisfy;
+
+output [ "x = [",] ++
+ [ show(i) ++ if j == n then "]\n;" else ", " endif
+ | j in 1..n, i in 1..n where j == fix(y[i]) ];
diff --git a/software/minizinc/docs/chi/examples/allinterval3.mzn b/software/minizinc/docs/chi/examples/allinterval3.mzn
new file mode 100644
index 0000000..336cd6f
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/allinterval3.mzn
@@ -0,0 +1,21 @@
+include "inverse.mzn";
+
+int: n;
+
+array[1..n] of var 1..n: x; % 数值的序列
+array[1..n-1] of var 1..n-1: u; % 差值的序列
+
+constraint forall(i in 1..n-1)(u[i] = abs(x[i+1] - x[i]));
+
+array[1..n] of var 1..n: y; % 每个数值的位置
+array[1..n-1] of var 1..n-1: v; % 差值的位置
+
+constraint inverse(x,y);
+constraint inverse(u,v);
+
+constraint abs(y[1] - y[n]) = 1 /\ v[n-1] = min(y[1], y[n]);
+
+solve :: int_search(y, first_fail, indomain_min, complete)
+ satisfy;
+
+output ["x = ",show(x),"\n"];
diff --git a/software/minizinc/docs/chi/examples/aust-enum.mzn b/software/minizinc/docs/chi/examples/aust-enum.mzn
new file mode 100644
index 0000000..93f7618
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/aust-enum.mzn
@@ -0,0 +1,11 @@
+enum Color;
+var Color: wa;
+var Color: nt;
+var Color: sa;
+var Color: q;
+var Color: nsw;
+var Color: v;
+var Color: t;
+constraint wa != nt /\ wa != sa /\ nt != sa /\ nt != q /\ sa != q;
+constraint sa != nsw /\ sa != v /\ q != nsw /\ nsw != v;
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/aust.mzn b/software/minizinc/docs/chi/examples/aust.mzn
new file mode 100644
index 0000000..1c4679c
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/aust.mzn
@@ -0,0 +1,20 @@
+% 用nc个颜色来涂澳大利亚
+int: nc = 3;
+
+var 1..nc: wa; var 1..nc: nt; var 1..nc: sa; var 1..nc: q;
+var 1..nc: nsw; var 1..nc: v; var 1..nc: t;
+
+constraint wa != nt;
+constraint wa != sa;
+constraint nt != sa;
+constraint nt != q;
+constraint sa != q;
+constraint sa != nsw;
+constraint sa != v;
+constraint q != nsw;
+constraint nsw != v;
+solve satisfy;
+
+output ["wa=\(wa)\t nt=\(nt)\t sa=\(sa)\n",
+ "q=\(q)\t nsw=\(nsw)\t v=\(v)\n",
+ "t=", show(t), "\n"];
diff --git a/software/minizinc/docs/chi/examples/bboolsum.mzn b/software/minizinc/docs/chi/examples/bboolsum.mzn
new file mode 100644
index 0000000..12beff8
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/bboolsum.mzn
@@ -0,0 +1,19 @@
+% 布尔型变量x的总和 = s
+predicate bool_sum_eq(array[int] of var bool:x, int:s) =
+ let { int: c = length(x) } in
+ if s < 0 then false
+ elseif s == 0 then
+ forall(i in 1..c)(x[i] == false)
+ elseif s < c then
+ let { % cp = number of bits required for representing 0..c
+ int: cp = floor(log2(int2float(c))),
+ % z is sum of x in binary
+ array[0..cp] of var bool:z } in
+ binary_sum(x, z) /\
+ % z == s
+ forall(i in 0..cp)(z[i] == ((s div pow(2,i)) mod 2 == 1))
+ elseif s == c then
+ forall(i in 1..c)(x[i] == true)
+ else false endif;
+
+include "binarysum.mzn";
diff --git a/software/minizinc/docs/chi/examples/bddsum.mzn b/software/minizinc/docs/chi/examples/bddsum.mzn
new file mode 100644
index 0000000..49eb00e
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/bddsum.mzn
@@ -0,0 +1,18 @@
+% the sum of booleans x = s
+predicate bool_sum_eq(array[int] of var bool:x, int:s) =
+ let { int: c = length(x),
+ array[1..c] of var bool: y = [x[i] | i in index_set(x)]
+ } in
+ rec_bool_sum_eq(y, 1, s);
+
+predicate rec_bool_sum_eq(array[int] of var bool:x, int: f, int:s) =
+ let { int: c = length(x) } in
+ if s < 0 then false
+ elseif s == 0 then
+ forall(i in f..c)(x[i] == false)
+ elseif s < c - f + 1 then
+ (x[f] == true /\ rec_bool_sum_eq(x,f+1,s-1)) \/
+ (x[f] == false /\ rec_bool_sum_eq(x,f+1,s))
+ elseif s == c - f + 1 then
+ forall(i in f..c)(x[i] == true)
+ else false endif;
diff --git a/software/minizinc/docs/chi/examples/binarysum.mzn b/software/minizinc/docs/chi/examples/binarysum.mzn
new file mode 100644
index 0000000..b5a5c0f
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/binarysum.mzn
@@ -0,0 +1,39 @@
+% 位 x 的的总和 = 二元表示的 s。
+% s[0], s[1], ..., s[k] 其中 2^k >= length(x) > 2^(k-1)
+predicate binary_sum(array[int] of var bool:x,
+ array[int] of var bool:s)=
+ let { int: l = length(x) } in
+ if l == 1 then s[0] = x[1]
+ elseif l == 2 then
+ s[0] = (x[1] xor x[2]) /\ s[1] = (x[1] /\ x[2])
+ else let { int: ll = (l div 2),
+ array[1..ll] of var bool: f = [ x[i] | i in 1..ll ],
+ array[1..ll] of var bool: t = [x[i]| i in ll+1..2*ll],
+ var bool: b = if ll*2 == l then false else x[l] endif,
+ int: cp = floor(log2(int2float(ll))),
+ array[0..cp] of var bool: fs,
+ array[0..cp] of var bool: ts } in
+ binary_sum(f, fs) /\ binary_sum(t, ts) /\
+ binary_add(fs, ts, b, s)
+ endif;
+
+% 把两个二元数值 x 和 y 加起来,位 ci 用来表示进位,来得到二元 s
+predicate binary_add(array[int] of var bool: x,
+ array[int] of var bool: y,
+ var bool: ci,
+ array[int] of var bool: s) =
+ let { int:l = length(x),
+ int:n = length(s), } in
+ assert(l == length(y),
+ "length of binary_add input args must be same",
+ assert(n == l \/ n == l+1, "length of binary_add output " ++
+ "must be equal or one more than inputs",
+ let { array[0..l] of var bool: c } in
+ full_adder(x[0], y[0], ci, s[0], c[0]) /\
+ forall(i in 1..l)(full_adder(x[i], y[i], c[i-1], s[i], c[i])) /\
+ if n > l then s[n] = c[l] else c[l] == false endif ));
+
+predicate full_adder(var bool: x, var bool: y, var bool: ci,
+ var bool: s, var bool: co) =
+ let { var bool: xy = x xor y } in
+ s = (xy xor ci) /\ co = ((x /\ y) \/ (ci /\ xy));
diff --git a/software/minizinc/docs/chi/examples/cakes.mzn b/software/minizinc/docs/chi/examples/cakes.mzn
new file mode 100644
index 0000000..2ea4f48
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cakes.mzn
@@ -0,0 +1,21 @@
+% 为校园游乐会做蛋糕
+
+var 0..100: b; % 香蕉蛋糕的个数
+var 0..100: c; % 巧克力蛋糕的个数
+
+% 面粉
+constraint 250*b + 200*c <= 4000;
+% 香蕉
+constraint 2*b <= 6;
+% 糖
+constraint 75*b + 150*c <= 2000;
+% 黄油
+constraint 100*b + 150*c <= 500;
+% 可可粉
+constraint 75*c <= 500;
+
+% 最大化我们的利润
+solve maximize 400*b + 450*c;
+
+output ["no. of banana cakes = \(b)\n",
+ "no. of chocolate cakes = \(c)\n"];
diff --git a/software/minizinc/docs/chi/examples/cakes2.mzn b/software/minizinc/docs/chi/examples/cakes2.mzn
new file mode 100644
index 0000000..664599a
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cakes2.mzn
@@ -0,0 +1,38 @@
+% 为校园游乐会做蛋糕(和数据文件一起)
+
+int: flour; %拥有的面粉克数
+int: banana; %拥有的香蕉个数
+int: sugar; %拥有的糖克数
+int: butter; %拥有的黄油克数
+int: cocoa; %拥有的可可粉克数
+
+constraint assert(flour >= 0,"Invalid datafile: " ++
+ "Amount of flour should be non-negative");
+constraint assert(banana >= 0,"Invalid datafile: " ++
+ "Amount of banana should be non-negative");
+constraint assert(sugar >= 0,"Invalid datafile: " ++
+ "Amount of sugar should be non-negative");
+constraint assert(butter >= 0,"Invalid datafile: " ++
+ "Amount of butter should be non-negative");
+constraint assert(cocoa >= 0,"Invalid datafile: " ++
+ "Amount of cocoa should be non-negative");
+
+var 0..100: b; % 香蕉蛋糕的个数
+var 0..100: c; % 巧克力蛋糕的个数
+
+% 面粉
+constraint 250*b + 200*c <= flour;
+% 香蕉
+constraint 2*b <= banana;
+% 糖
+constraint 75*b + 150*c <= sugar;
+% 黄油
+constraint 100*b + 150*c <= butter;
+% 可可粉
+constraint 75*c <= cocoa;
+
+% 最大化我们的利润
+solve maximize 400*b + 450*c;
+
+output ["no. of banana cakes = \(b)\n",
+ "no. of chocolate cakes = \(c)\n"];
diff --git a/software/minizinc/docs/chi/examples/cars.mzn b/software/minizinc/docs/chi/examples/cars.mzn
new file mode 100644
index 0000000..93a4af7
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cars.mzn
@@ -0,0 +1,35 @@
+% cars.mzn
+include "globals.mzn";
+
+int: n_cars; int: n_options; int: n_classes;
+
+set of int: steps = 1..n_cars;
+set of int: options = 1..n_options;
+set of int: classes = 1..n_classes;
+
+array [options] of int: max_per_block;
+array [options] of int: block_size;
+array [classes] of int: cars_in_class;
+array [classes, options] of 0..1: need;
+
+% The class of car being started at each step.
+array [steps] of var classes: class;
+
+% Which options are required by the car started at each step.
+array [steps, options] of var 0..1: used;
+
+% Block p must be used at step s if the class of the car to be
+% produced at step s needs it.
+constraint forall (s in steps, p in options) (used[s, p]=need[class[s], p]);
+
+% For each option p with block size b and maximum limit m, no consecutive
+% sequence of b cars contains more than m that require option p.
+constraint
+ forall (p in options, i in 1..(n_cars - (block_size[p] - 1))) (
+ sum (j in 0..(block_size[p] - 1)) (used[i + j, p])
+ <= max_per_block[p]);
+
+% Require that the right number of cars in each class are produced.
+constraint forall (c in classes) (count(class, c, cars_in_class[c]));
+
+solve satisfy; % Find any solution.
diff --git a/software/minizinc/docs/chi/examples/cars_data.dzn b/software/minizinc/docs/chi/examples/cars_data.dzn
new file mode 100644
index 0000000..f721e44
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cars_data.dzn
@@ -0,0 +1,16 @@
+% cars_data.dzn
+n_cars = 10;
+n_options = 5;
+n_classes = 6;
+max_per_block = [1, 2, 1, 2, 1];
+block_size = [2, 3, 3, 5, 5];
+cars_in_class = [1, 1, 2, 2, 2, 2];
+
+need = array2d(1..6, 1..5, [
+ 1, 0, 1, 1, 0,
+ 0, 0, 0, 1, 0,
+ 0, 1, 0, 0, 1,
+ 0, 1, 0, 1, 0,
+ 1, 0, 1, 0, 0,
+ 1, 1, 0, 0, 0
+]);
diff --git a/software/minizinc/docs/chi/examples/cnonoverlap.fzn b/software/minizinc/docs/chi/examples/cnonoverlap.fzn
new file mode 100644
index 0000000..e2ff958
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cnonoverlap.fzn
@@ -0,0 +1,19 @@
+% 变量
+var 2.0 .. 8.0: x1;
+var 2.0 .. 6.0: y1;
+var 3.0 .. 7.0: x2;
+var 3.0 .. 5.0: y2;
+%
+var -5.0..5.0: FLOAT01;
+var -25.0..25.0: FLOAT02;
+var -3.0..3.0: FLOAT03;
+var -9.0..9.0: FLOAT04;
+var 25.0..34.0: FLOAT05;
+% 约束
+constraint float_plus(FLOAT01, x2, x1);
+constraint float_plus(FLOAT03, y2, y1);
+constraint float_plus(FLOAT02, FLOAT04, FLOAT05);
+constraint float_times(FLOAT01, FLOAT01, FLOAT02);
+constraint float_times(FLOAT03, FLOAT03, FLOAT04);
+%
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/cnonoverlap.mzn b/software/minizinc/docs/chi/examples/cnonoverlap.mzn
new file mode 100644
index 0000000..5ef784d
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/cnonoverlap.mzn
@@ -0,0 +1,11 @@
+float: width; % 包含圆的长方形的宽
+float: height; % 包含圆的长方形的高
+float: r1;
+var r1..width-r1: x1; % (x1,y1) 是第一个圆的中心
+var r1..height-r1: y1;
+float: r2;
+var r2..width-r2: x2; % (x2,y2) 是第二个圆的中心
+var r2..height-r2: y2;
+ % 中心之间至少有r1 + r2的距离
+constraint (x1-x2)*(x1-x2) + (y1-y2)*(y1-y2) >= (r1+r2)*(r1+r2);
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/command_line/data.dzn b/software/minizinc/docs/chi/examples/command_line/data.dzn
new file mode 100644
index 0000000..ffd86cd
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/command_line/data.dzn
@@ -0,0 +1 @@
+n = 5;
diff --git a/software/minizinc/docs/chi/examples/command_line/model.mzn b/software/minizinc/docs/chi/examples/command_line/model.mzn
new file mode 100644
index 0000000..bf9863f
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/command_line/model.mzn
@@ -0,0 +1,6 @@
+int: n;
+array[1..n] of var 1..2*n: x;
+include "alldifferent.mzn";
+constraint alldifferent(x);
+solve maximize sum(x);
+output ["The resulting values are \(x).\n"];
diff --git a/software/minizinc/docs/chi/examples/count1.mzn b/software/minizinc/docs/chi/examples/count1.mzn
new file mode 100644
index 0000000..1aff6bb
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/count1.mzn
@@ -0,0 +1,15 @@
+% ignore
+int:n;
+set of int: NODES = 1..n;
+array [NODES,NODES] of bool: adj;
+bool: t = true;
+bool: f = false;
+n = 4;
+int:count=sum([ 1 | i,j,k in NODES where
+ trace("+", i= 0 and r[i] >= 0
+%--------------------------------------------------------------------%
+predicate cumulative(array[int] of var int: s,
+ array[int] of var int: d,
+ array[int] of var int: r, var int: b) =
+ assert(index_set(s) == index_set(d) /\
+ index_set(s) == index_set(r),
+ "cumulative: the array arguments must have identical index sets",
+ assert(lb_array(d) >= 0 /\ lb_array(r) >= 0,
+ "cumulative: durations and resource usages must be non-negative",
+ let {
+ set of int: times =
+ lb_array(s) ..
+ max([ ub(s[i]) + ub(d[i]) | i in index_set(s) ])
+ }
+ in
+ forall( t in times ) (
+ b >= sum( i in index_set(s) ) (
+ bool2int( s[i] <= t /\ t < s[i] + d[i] ) * r[i]
+ )
+ )
+ )
+ );
diff --git a/software/minizinc/docs/chi/examples/disjunctive.mzn b/software/minizinc/docs/chi/examples/disjunctive.mzn
new file mode 100644
index 0000000..a44a1df
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/disjunctive.mzn
@@ -0,0 +1,7 @@
+include "cumulative.mzn";
+
+predicate disjunctive(array[int] of var int:s, array[int] of int:d) =
+ assert(index_set(s) == index_set(d), "disjunctive: " ++
+ "first and second arguments must have the same index set",
+ cumulative(s, d, [ 1 | i in index_set(s) ], 1)
+ );
diff --git a/software/minizinc/docs/chi/examples/dummy.mzn b/software/minizinc/docs/chi/examples/dummy.mzn
new file mode 100644
index 0000000..0b11856
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/dummy.mzn
@@ -0,0 +1,3 @@
+% Just an example
+var int: x;
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/flexible-js.mzn b/software/minizinc/docs/chi/examples/flexible-js.mzn
new file mode 100644
index 0000000..9b0f84d
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/flexible-js.mzn
@@ -0,0 +1,22 @@
+include "globals.mzn";
+
+int: horizon; % 时间范围
+set of int: Time = 0..horizon;
+enum Task;
+enum Machine;
+
+array[Task,Machine] of int: d; % 每个机器上的持续时间
+int: maxd = max([ d[t,m] | t in Task, m in Machine ]);
+int: mind = min([ d[t,m] | t in Task, m in Machine ]);
+
+array[Task] of var Time: S; % 起始时间
+array[Task] of var mind..maxd: D; % 持续时间
+array[Task,Machine] of var opt Time: O; % 可选择的任务起始
+
+constraint forall(t in Task)(alternative(S[t],D[t],
+ [O[t,m]|m in Machine],[d[t,m]|m in Machine]));
+constraint forall(m in Machine)
+ (disjunctive([O[t,m]|t in Task],[d[t,m]|t in Task]));
+constraint cumulative(S,D,[1|i in Task],card(Machine));
+
+solve minimize max(t in Task)(S[t] + D[t]);
diff --git a/software/minizinc/docs/chi/examples/golomb.mzn b/software/minizinc/docs/chi/examples/golomb.mzn
new file mode 100644
index 0000000..39cad46
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/golomb.mzn
@@ -0,0 +1,18 @@
+include "alldifferent.mzn";
+
+int: n; % number of marks on ruler
+int: m; % max length of ruler
+
+array[1..n] of var 0..m: mark;
+array[1..n,1..n] of var 0..m: diffs;
+
+constraint mark[1] = 0;
+constraint forall ( i in 1..n-1 ) ( mark[i] < mark[i+1] );
+constraint forall (i,j in 1..n where i > j) % (diff)
+ (diffs[i,j] = mark[i] - mark[j]); % (diff)
+constraint alldifferent([ diffs[i,j] | i,j in 1..n where i > j]);
+constraint diffs[2,1] < diffs[n,n-1]; % symmetry break
+
+solve satisfy;
+
+output ["marks = ",show(mark),"\n"];
diff --git a/software/minizinc/docs/chi/examples/grocery.mzn b/software/minizinc/docs/chi/examples/grocery.mzn
new file mode 100644
index 0000000..30e4201
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/grocery.mzn
@@ -0,0 +1,15 @@
+var int: item1;
+var int: item2;
+var int: item3;
+var int: item4;
+
+constraint item1 + item2 + item3 + item4 == 711;
+constraint item1 * item2 * item3 * item4 == 711 * 100 * 100 * 100;
+
+constraint 0 < item1 /\ item1 <= item2
+ /\ item2 <= item3 /\ item3 <= item4;
+
+solve satisfy;
+
+output ["{", show(item1), ",", show(item2), ",", show(item3), ",",
+ show(item4),"}\n"];
diff --git a/software/minizinc/docs/chi/examples/inverse.mzn b/software/minizinc/docs/chi/examples/inverse.mzn
new file mode 100644
index 0000000..dc1049a
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/inverse.mzn
@@ -0,0 +1,7 @@
+predicate inverse(array[int] of var int: f,
+ array[int] of var int: invf) =
+ forall(j in index_set(invf))(invf[j] in index_set(f)) /\
+ forall(i in index_set(f))(
+ f[i] in index_set(invf) /\
+ forall(j in index_set(invf))(j == f[i] <-> i == invf[j])
+ );
diff --git a/software/minizinc/docs/chi/examples/jdata.dzn b/software/minizinc/docs/chi/examples/jdata.dzn
new file mode 100644
index 0000000..d5786ba
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jdata.dzn
@@ -0,0 +1,7 @@
+JOB = anon_enum(5);
+TASK = anon_enum(5);
+d = [| 1, 4, 5, 3, 6
+ | 3, 2, 7, 1, 2
+ | 4, 4, 4, 4, 4
+ | 1, 1, 1, 6, 8
+ | 7, 3, 2, 2, 1 |];
diff --git a/software/minizinc/docs/chi/examples/jobshop.fzn b/software/minizinc/docs/chi/examples/jobshop.fzn
new file mode 100644
index 0000000..250e91b
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jobshop.fzn
@@ -0,0 +1,298 @@
+array [1..2] of int: X_INTRODUCED_28 = [1,-1];
+var 0..86: X_INTRODUCED_0;
+var 0..86: X_INTRODUCED_1;
+var 0..86: X_INTRODUCED_2;
+var 0..86: X_INTRODUCED_3;
+var 0..24: X_INTRODUCED_4;
+var 0..86: X_INTRODUCED_5;
+var 0..86: X_INTRODUCED_6;
+var 0..86: X_INTRODUCED_7;
+var 0..86: X_INTRODUCED_8;
+var 0..28: X_INTRODUCED_9;
+var 0..86: X_INTRODUCED_10;
+var 0..86: X_INTRODUCED_11;
+var 0..86: X_INTRODUCED_12;
+var 0..86: X_INTRODUCED_13;
+var 0..26: X_INTRODUCED_14;
+var 0..86: X_INTRODUCED_15;
+var 0..86: X_INTRODUCED_16;
+var 0..86: X_INTRODUCED_17;
+var 0..86: X_INTRODUCED_18;
+var 0..22: X_INTRODUCED_19;
+var 0..86: X_INTRODUCED_20;
+var 0..86: X_INTRODUCED_21;
+var 0..86: X_INTRODUCED_22;
+var 0..86: X_INTRODUCED_23;
+var 0..29: X_INTRODUCED_24;
+var bool: X_INTRODUCED_52 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_53 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_54 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_55 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_56 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_57 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_58 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_59 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_60 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_61 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_62 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_63 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_64 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_65 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_66 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_67 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_68 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_69 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_70 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_71 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_72 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_73 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_74 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_75 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_76 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_77 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_78 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_79 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_80 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_81 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_82 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_83 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_84 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_85 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_86 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_87 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_88 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_89 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_90 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_91 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_92 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_93 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_94 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_95 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_96 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_97 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_98 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_99 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_100 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_101 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_102 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_103 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_104 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_105 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_106 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_107 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_108 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_109 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_110 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_111 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_112 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_113 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_114 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_115 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_116 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_117 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_118 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_119 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_120 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_121 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_122 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_123 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_124 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_125 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_126 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_127 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_128 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_129 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_130 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_131 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_132 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_133 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_134 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_135 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_136 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_137 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_138 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_139 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_140 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_141 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_142 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_143 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_144 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_145 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_146 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_147 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_148 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_149 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_150 ::var_is_introduced :: is_defined_var;
+var bool: X_INTRODUCED_151 ::var_is_introduced :: is_defined_var;
+array [1..25] of var int: s:: output_array([1..5,1..5]) = [X_INTRODUCED_0,X_INTRODUCED_1,X_INTRODUCED_2,X_INTRODUCED_3,X_INTRODUCED_4,X_INTRODUCED_5,X_INTRODUCED_6,X_INTRODUCED_7,X_INTRODUCED_8,X_INTRODUCED_9,X_INTRODUCED_10,X_INTRODUCED_11,X_INTRODUCED_12,X_INTRODUCED_13,X_INTRODUCED_14,X_INTRODUCED_15,X_INTRODUCED_16,X_INTRODUCED_17,X_INTRODUCED_18,X_INTRODUCED_19,X_INTRODUCED_20,X_INTRODUCED_21,X_INTRODUCED_22,X_INTRODUCED_23,X_INTRODUCED_24];
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_0,X_INTRODUCED_1],-1);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_1,X_INTRODUCED_2],-4);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_2,X_INTRODUCED_3],-5);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_3,X_INTRODUCED_4],-3);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_5,X_INTRODUCED_6],-3);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_6,X_INTRODUCED_7],-2);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_7,X_INTRODUCED_8],-7);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_8,X_INTRODUCED_9],-1);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_10,X_INTRODUCED_11],-4);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_11,X_INTRODUCED_12],-4);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_12,X_INTRODUCED_13],-4);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_13,X_INTRODUCED_14],-4);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_15,X_INTRODUCED_16],-1);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_16,X_INTRODUCED_17],-1);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_17,X_INTRODUCED_18],-1);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_18,X_INTRODUCED_19],-6);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_20,X_INTRODUCED_21],-7);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_21,X_INTRODUCED_22],-3);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_22,X_INTRODUCED_23],-2);
+constraint int_lin_le(X_INTRODUCED_28,[X_INTRODUCED_23,X_INTRODUCED_24],-2);
+constraint array_bool_or([X_INTRODUCED_52,X_INTRODUCED_53],true);
+constraint array_bool_or([X_INTRODUCED_54,X_INTRODUCED_55],true);
+constraint array_bool_or([X_INTRODUCED_56,X_INTRODUCED_57],true);
+constraint array_bool_or([X_INTRODUCED_59,X_INTRODUCED_58],true);
+constraint array_bool_or([X_INTRODUCED_61,X_INTRODUCED_60],true);
+constraint array_bool_or([X_INTRODUCED_63,X_INTRODUCED_62],true);
+constraint array_bool_or([X_INTRODUCED_65,X_INTRODUCED_64],true);
+constraint array_bool_or([X_INTRODUCED_67,X_INTRODUCED_66],true);
+constraint array_bool_or([X_INTRODUCED_69,X_INTRODUCED_68],true);
+constraint array_bool_or([X_INTRODUCED_71,X_INTRODUCED_70],true);
+constraint array_bool_or([X_INTRODUCED_73,X_INTRODUCED_72],true);
+constraint array_bool_or([X_INTRODUCED_75,X_INTRODUCED_74],true);
+constraint array_bool_or([X_INTRODUCED_77,X_INTRODUCED_76],true);
+constraint array_bool_or([X_INTRODUCED_78,X_INTRODUCED_79],true);
+constraint array_bool_or([X_INTRODUCED_80,X_INTRODUCED_81],true);
+constraint array_bool_or([X_INTRODUCED_82,X_INTRODUCED_83],true);
+constraint array_bool_or([X_INTRODUCED_84,X_INTRODUCED_85],true);
+constraint array_bool_or([X_INTRODUCED_86,X_INTRODUCED_87],true);
+constraint array_bool_or([X_INTRODUCED_88,X_INTRODUCED_89],true);
+constraint array_bool_or([X_INTRODUCED_90,X_INTRODUCED_91],true);
+constraint array_bool_or([X_INTRODUCED_92,X_INTRODUCED_93],true);
+constraint array_bool_or([X_INTRODUCED_94,X_INTRODUCED_95],true);
+constraint array_bool_or([X_INTRODUCED_96,X_INTRODUCED_97],true);
+constraint array_bool_or([X_INTRODUCED_98,X_INTRODUCED_99],true);
+constraint array_bool_or([X_INTRODUCED_100,X_INTRODUCED_101],true);
+constraint array_bool_or([X_INTRODUCED_102,X_INTRODUCED_103],true);
+constraint array_bool_or([X_INTRODUCED_104,X_INTRODUCED_105],true);
+constraint array_bool_or([X_INTRODUCED_106,X_INTRODUCED_107],true);
+constraint array_bool_or([X_INTRODUCED_108,X_INTRODUCED_109],true);
+constraint array_bool_or([X_INTRODUCED_110,X_INTRODUCED_111],true);
+constraint array_bool_or([X_INTRODUCED_112,X_INTRODUCED_113],true);
+constraint array_bool_or([X_INTRODUCED_114,X_INTRODUCED_115],true);
+constraint array_bool_or([X_INTRODUCED_116,X_INTRODUCED_117],true);
+constraint array_bool_or([X_INTRODUCED_118,X_INTRODUCED_119],true);
+constraint array_bool_or([X_INTRODUCED_120,X_INTRODUCED_121],true);
+constraint array_bool_or([X_INTRODUCED_122,X_INTRODUCED_123],true);
+constraint array_bool_or([X_INTRODUCED_124,X_INTRODUCED_125],true);
+constraint array_bool_or([X_INTRODUCED_126,X_INTRODUCED_127],true);
+constraint array_bool_or([X_INTRODUCED_128,X_INTRODUCED_129],true);
+constraint array_bool_or([X_INTRODUCED_130,X_INTRODUCED_131],true);
+constraint array_bool_or([X_INTRODUCED_132,X_INTRODUCED_133],true);
+constraint array_bool_or([X_INTRODUCED_134,X_INTRODUCED_135],true);
+constraint array_bool_or([X_INTRODUCED_136,X_INTRODUCED_137],true);
+constraint array_bool_or([X_INTRODUCED_138,X_INTRODUCED_139],true);
+constraint array_bool_or([X_INTRODUCED_140,X_INTRODUCED_141],true);
+constraint array_bool_or([X_INTRODUCED_142,X_INTRODUCED_143],true);
+constraint array_bool_or([X_INTRODUCED_144,X_INTRODUCED_145],true);
+constraint array_bool_or([X_INTRODUCED_146,X_INTRODUCED_147],true);
+constraint array_bool_or([X_INTRODUCED_148,X_INTRODUCED_149],true);
+constraint array_bool_or([X_INTRODUCED_150,X_INTRODUCED_151],true);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_5,X_INTRODUCED_0],-3,X_INTRODUCED_52):: defines_var(X_INTRODUCED_52);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_0,X_INTRODUCED_5],-1,X_INTRODUCED_53):: defines_var(X_INTRODUCED_53);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_10,X_INTRODUCED_0],-4,X_INTRODUCED_54):: defines_var(X_INTRODUCED_54);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_0,X_INTRODUCED_10],-1,X_INTRODUCED_55):: defines_var(X_INTRODUCED_55);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_15,X_INTRODUCED_0],-1,X_INTRODUCED_56):: defines_var(X_INTRODUCED_56);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_0,X_INTRODUCED_15],-1,X_INTRODUCED_57):: defines_var(X_INTRODUCED_57);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_20,X_INTRODUCED_0],-7,X_INTRODUCED_58):: defines_var(X_INTRODUCED_58);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_0,X_INTRODUCED_20],-1,X_INTRODUCED_59):: defines_var(X_INTRODUCED_59);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_10,X_INTRODUCED_5],-4,X_INTRODUCED_60):: defines_var(X_INTRODUCED_60);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_5,X_INTRODUCED_10],-3,X_INTRODUCED_61):: defines_var(X_INTRODUCED_61);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_15,X_INTRODUCED_5],-1,X_INTRODUCED_62):: defines_var(X_INTRODUCED_62);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_5,X_INTRODUCED_15],-3,X_INTRODUCED_63):: defines_var(X_INTRODUCED_63);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_20,X_INTRODUCED_5],-7,X_INTRODUCED_64):: defines_var(X_INTRODUCED_64);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_5,X_INTRODUCED_20],-3,X_INTRODUCED_65):: defines_var(X_INTRODUCED_65);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_15,X_INTRODUCED_10],-1,X_INTRODUCED_66):: defines_var(X_INTRODUCED_66);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_10,X_INTRODUCED_15],-4,X_INTRODUCED_67):: defines_var(X_INTRODUCED_67);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_20,X_INTRODUCED_10],-7,X_INTRODUCED_68):: defines_var(X_INTRODUCED_68);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_10,X_INTRODUCED_20],-4,X_INTRODUCED_69):: defines_var(X_INTRODUCED_69);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_20,X_INTRODUCED_15],-7,X_INTRODUCED_70):: defines_var(X_INTRODUCED_70);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_15,X_INTRODUCED_20],-1,X_INTRODUCED_71):: defines_var(X_INTRODUCED_71);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_6,X_INTRODUCED_1],-2,X_INTRODUCED_72):: defines_var(X_INTRODUCED_72);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_1,X_INTRODUCED_6],-4,X_INTRODUCED_73):: defines_var(X_INTRODUCED_73);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_11,X_INTRODUCED_1],-4,X_INTRODUCED_74):: defines_var(X_INTRODUCED_74);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_1,X_INTRODUCED_11],-4,X_INTRODUCED_75):: defines_var(X_INTRODUCED_75);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_16,X_INTRODUCED_1],-1,X_INTRODUCED_76):: defines_var(X_INTRODUCED_76);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_1,X_INTRODUCED_16],-4,X_INTRODUCED_77):: defines_var(X_INTRODUCED_77);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_21,X_INTRODUCED_1],-3,X_INTRODUCED_78):: defines_var(X_INTRODUCED_78);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_1,X_INTRODUCED_21],-4,X_INTRODUCED_79):: defines_var(X_INTRODUCED_79);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_11,X_INTRODUCED_6],-4,X_INTRODUCED_80):: defines_var(X_INTRODUCED_80);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_6,X_INTRODUCED_11],-2,X_INTRODUCED_81):: defines_var(X_INTRODUCED_81);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_16,X_INTRODUCED_6],-1,X_INTRODUCED_82):: defines_var(X_INTRODUCED_82);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_6,X_INTRODUCED_16],-2,X_INTRODUCED_83):: defines_var(X_INTRODUCED_83);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_21,X_INTRODUCED_6],-3,X_INTRODUCED_84):: defines_var(X_INTRODUCED_84);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_6,X_INTRODUCED_21],-2,X_INTRODUCED_85):: defines_var(X_INTRODUCED_85);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_16,X_INTRODUCED_11],-1,X_INTRODUCED_86):: defines_var(X_INTRODUCED_86);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_11,X_INTRODUCED_16],-4,X_INTRODUCED_87):: defines_var(X_INTRODUCED_87);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_21,X_INTRODUCED_11],-3,X_INTRODUCED_88):: defines_var(X_INTRODUCED_88);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_11,X_INTRODUCED_21],-4,X_INTRODUCED_89):: defines_var(X_INTRODUCED_89);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_21,X_INTRODUCED_16],-3,X_INTRODUCED_90):: defines_var(X_INTRODUCED_90);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_16,X_INTRODUCED_21],-1,X_INTRODUCED_91):: defines_var(X_INTRODUCED_91);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_7,X_INTRODUCED_2],-7,X_INTRODUCED_92):: defines_var(X_INTRODUCED_92);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_2,X_INTRODUCED_7],-5,X_INTRODUCED_93):: defines_var(X_INTRODUCED_93);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_12,X_INTRODUCED_2],-4,X_INTRODUCED_94):: defines_var(X_INTRODUCED_94);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_2,X_INTRODUCED_12],-5,X_INTRODUCED_95):: defines_var(X_INTRODUCED_95);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_17,X_INTRODUCED_2],-1,X_INTRODUCED_96):: defines_var(X_INTRODUCED_96);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_2,X_INTRODUCED_17],-5,X_INTRODUCED_97):: defines_var(X_INTRODUCED_97);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_22,X_INTRODUCED_2],-2,X_INTRODUCED_98):: defines_var(X_INTRODUCED_98);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_2,X_INTRODUCED_22],-5,X_INTRODUCED_99):: defines_var(X_INTRODUCED_99);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_12,X_INTRODUCED_7],-4,X_INTRODUCED_100):: defines_var(X_INTRODUCED_100);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_7,X_INTRODUCED_12],-7,X_INTRODUCED_101):: defines_var(X_INTRODUCED_101);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_17,X_INTRODUCED_7],-1,X_INTRODUCED_102):: defines_var(X_INTRODUCED_102);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_7,X_INTRODUCED_17],-7,X_INTRODUCED_103):: defines_var(X_INTRODUCED_103);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_22,X_INTRODUCED_7],-2,X_INTRODUCED_104):: defines_var(X_INTRODUCED_104);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_7,X_INTRODUCED_22],-7,X_INTRODUCED_105):: defines_var(X_INTRODUCED_105);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_17,X_INTRODUCED_12],-1,X_INTRODUCED_106):: defines_var(X_INTRODUCED_106);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_12,X_INTRODUCED_17],-4,X_INTRODUCED_107):: defines_var(X_INTRODUCED_107);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_22,X_INTRODUCED_12],-2,X_INTRODUCED_108):: defines_var(X_INTRODUCED_108);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_12,X_INTRODUCED_22],-4,X_INTRODUCED_109):: defines_var(X_INTRODUCED_109);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_22,X_INTRODUCED_17],-2,X_INTRODUCED_110):: defines_var(X_INTRODUCED_110);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_17,X_INTRODUCED_22],-1,X_INTRODUCED_111):: defines_var(X_INTRODUCED_111);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_8,X_INTRODUCED_3],-1,X_INTRODUCED_112):: defines_var(X_INTRODUCED_112);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_3,X_INTRODUCED_8],-3,X_INTRODUCED_113):: defines_var(X_INTRODUCED_113);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_13,X_INTRODUCED_3],-4,X_INTRODUCED_114):: defines_var(X_INTRODUCED_114);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_3,X_INTRODUCED_13],-3,X_INTRODUCED_115):: defines_var(X_INTRODUCED_115);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_18,X_INTRODUCED_3],-6,X_INTRODUCED_116):: defines_var(X_INTRODUCED_116);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_3,X_INTRODUCED_18],-3,X_INTRODUCED_117):: defines_var(X_INTRODUCED_117);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_23,X_INTRODUCED_3],-2,X_INTRODUCED_118):: defines_var(X_INTRODUCED_118);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_3,X_INTRODUCED_23],-3,X_INTRODUCED_119):: defines_var(X_INTRODUCED_119);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_13,X_INTRODUCED_8],-4,X_INTRODUCED_120):: defines_var(X_INTRODUCED_120);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_8,X_INTRODUCED_13],-1,X_INTRODUCED_121):: defines_var(X_INTRODUCED_121);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_18,X_INTRODUCED_8],-6,X_INTRODUCED_122):: defines_var(X_INTRODUCED_122);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_8,X_INTRODUCED_18],-1,X_INTRODUCED_123):: defines_var(X_INTRODUCED_123);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_23,X_INTRODUCED_8],-2,X_INTRODUCED_124):: defines_var(X_INTRODUCED_124);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_8,X_INTRODUCED_23],-1,X_INTRODUCED_125):: defines_var(X_INTRODUCED_125);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_18,X_INTRODUCED_13],-6,X_INTRODUCED_126):: defines_var(X_INTRODUCED_126);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_13,X_INTRODUCED_18],-4,X_INTRODUCED_127):: defines_var(X_INTRODUCED_127);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_23,X_INTRODUCED_13],-2,X_INTRODUCED_128):: defines_var(X_INTRODUCED_128);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_13,X_INTRODUCED_23],-4,X_INTRODUCED_129):: defines_var(X_INTRODUCED_129);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_23,X_INTRODUCED_18],-2,X_INTRODUCED_130):: defines_var(X_INTRODUCED_130);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_18,X_INTRODUCED_23],-6,X_INTRODUCED_131):: defines_var(X_INTRODUCED_131);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_9,X_INTRODUCED_4],-2,X_INTRODUCED_132):: defines_var(X_INTRODUCED_132);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_4,X_INTRODUCED_9],-6,X_INTRODUCED_133):: defines_var(X_INTRODUCED_133);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_14,X_INTRODUCED_4],-4,X_INTRODUCED_134):: defines_var(X_INTRODUCED_134);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_4,X_INTRODUCED_14],-6,X_INTRODUCED_135):: defines_var(X_INTRODUCED_135);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_19,X_INTRODUCED_4],-8,X_INTRODUCED_136):: defines_var(X_INTRODUCED_136);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_4,X_INTRODUCED_19],-6,X_INTRODUCED_137):: defines_var(X_INTRODUCED_137);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_24,X_INTRODUCED_4],-1,X_INTRODUCED_138):: defines_var(X_INTRODUCED_138);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_4,X_INTRODUCED_24],-6,X_INTRODUCED_139):: defines_var(X_INTRODUCED_139);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_14,X_INTRODUCED_9],-4,X_INTRODUCED_140):: defines_var(X_INTRODUCED_140);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_9,X_INTRODUCED_14],-2,X_INTRODUCED_141):: defines_var(X_INTRODUCED_141);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_19,X_INTRODUCED_9],-8,X_INTRODUCED_142):: defines_var(X_INTRODUCED_142);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_9,X_INTRODUCED_19],-2,X_INTRODUCED_143):: defines_var(X_INTRODUCED_143);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_24,X_INTRODUCED_9],-1,X_INTRODUCED_144):: defines_var(X_INTRODUCED_144);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_9,X_INTRODUCED_24],-2,X_INTRODUCED_145):: defines_var(X_INTRODUCED_145);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_19,X_INTRODUCED_14],-8,X_INTRODUCED_146):: defines_var(X_INTRODUCED_146);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_14,X_INTRODUCED_19],-4,X_INTRODUCED_147):: defines_var(X_INTRODUCED_147);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_24,X_INTRODUCED_14],-1,X_INTRODUCED_148):: defines_var(X_INTRODUCED_148);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_14,X_INTRODUCED_24],-4,X_INTRODUCED_149):: defines_var(X_INTRODUCED_149);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_24,X_INTRODUCED_19],-1,X_INTRODUCED_150):: defines_var(X_INTRODUCED_150);
+constraint int_lin_le_reif(X_INTRODUCED_28,[X_INTRODUCED_19,X_INTRODUCED_24],-8,X_INTRODUCED_151):: defines_var(X_INTRODUCED_151);
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/jobshop.mzn b/software/minizinc/docs/chi/examples/jobshop.mzn
new file mode 100644
index 0000000..977c7a9
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jobshop.mzn
@@ -0,0 +1,31 @@
+enum JOB;
+enum TASK;
+TASK: last = max(TASK);
+array [JOB,TASK] of int: d; % 任务持续时间
+int: total = sum(i in JOB, j in TASK)(d[i,j]);% 总持续时间
+int: digs = ceil(log(10.0,int2float(total))); % 输出的数值
+array [JOB,TASK] of var 0..total: s; % 起始时间
+var 0..total: end; % 总结束时间
+
+
+constraint %% 保证任务按照顺序出现
+ forall(i in JOB) (
+ forall(j in TASK where j < last)
+ (s[i,j] + d[i,j] <= s[i,enum_next(TASK,j)]) /\
+ s[i,last] + d[i,last] <= end
+ );
+
+constraint %% 保证任务之间没有重叠
+ forall(j in TASK) (
+ forall(i,k in JOB where i < k) (
+ s[i,j] + d[i,j] <= s[k,j] \/
+ s[k,j] + d[k,j] <= s[i,j]
+ )
+ );
+
+solve minimize end;
+
+output ["end = \(end)\n"] ++
+ [ show_int(digs,s[i,j]) ++ " " ++
+ if j == last then "\n" else "" endif |
+ i in JOB, j in TASK ];
diff --git a/software/minizinc/docs/chi/examples/jobshop.ozn b/software/minizinc/docs/chi/examples/jobshop.ozn
new file mode 100644
index 0000000..be60fc7
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jobshop.ozn
@@ -0,0 +1,7 @@
+output ["end = "++format(end)++"\n"]++[(show_int(digs,s[i,j])++" ")++if j==last then "\n" else "" endif | i in JOB, j in TASK, ];
+set of int: JOB = 1..5;
+set of int: TASK = 1..5;
+int: last = 5;
+int: digs = 2;
+array [JOB,TASK] of int: s;
+int: end = 30;
diff --git a/software/minizinc/docs/chi/examples/jobshop2.mzn b/software/minizinc/docs/chi/examples/jobshop2.mzn
new file mode 100644
index 0000000..89d34b9
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jobshop2.mzn
@@ -0,0 +1,34 @@
+int: jobs; % 作业的数量
+set of int: JOB = 1..jobs;
+int: tasks; % 每个作业的任务数量
+set of int: TASK = 1..tasks;
+array [JOB,TASK] of int: d; % 任务持续时间
+int: total = sum(i in JOB, j in TASK)(d[i,j]);% 总持续时间
+int: digs = ceil(log(10.0,total)); % 输出的数值
+array [JOB,TASK] of var 0..total: s; % 起始时间
+var 0..total: end; % 总结束时间
+
+% nooverlap
+predicate no_overlap(var int:s1, int:d1, var int:s2, int:d2) =
+ s1 + d1 <= s2 \/ s2 + d2 <= s1;
+
+constraint %% 保证任务按照顺序出现
+ forall(i in JOB) (
+ forall(j in 1..tasks-1)
+ (s[i,j] + d[i,j] <= s[i,j+1]) /\
+ s[i,tasks] + d[i,tasks] <= end
+ );
+
+constraint %% 保证任务之间没有重叠
+ forall(j in TASK) (
+ forall(i,k in JOB where i < k) (
+ no_overlap(s[i,j], d[i,j], s[k,j], d[k,j])
+ )
+ );
+
+solve minimize end;
+
+output ["end = \(end)\n"] ++
+ [ show_int(digs,s[i,j]) ++ " " ++
+ if j == tasks then "\n" else "" endif |
+ i in JOB, j in TASK ];
diff --git a/software/minizinc/docs/chi/examples/jobshop3.mzn b/software/minizinc/docs/chi/examples/jobshop3.mzn
new file mode 100644
index 0000000..50ac77b
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/jobshop3.mzn
@@ -0,0 +1,30 @@
+include "disjunctive.mzn";
+
+int: jobs; % 作业的数量
+set of int: JOB = 1..jobs;
+int: tasks; % 每个作业的任务数量
+set of int: TASK = 1..tasks;
+array [JOB,TASK] of int: d; % 任务持续时间
+int: total = sum(i in JOB, j in TASK)(d[i,j]);% 总持续时间
+int: digs = ceil(log(10.0,total)); % 输出的数值
+array [JOB,TASK] of var 0..total: s; % 起始时间
+var 0..total: end; % 总结束时间
+
+constraint %% 保证任务按照顺序出现
+ forall(i in JOB) (
+ forall(j in 1..tasks-1)
+ (s[i,j] + d[i,j] <= s[i,j+1]) /\
+ s[i,tasks] + d[i,tasks] <= end
+ );
+
+constraint %% 保证任务之间没有重叠
+ forall(j in TASK) (
+ disjunctive([s[i,j] | i in JOB], [d[i,j] | i in JOB])
+ );
+
+solve minimize end;
+
+output ["end = \(end)\n"] ++
+ [ show_int(digs,s[i,j]) ++ " " ++
+ if j == tasks then "\n" else "" endif |
+ i in JOB, j in TASK ];
diff --git a/software/minizinc/docs/chi/examples/knapsack.mzn b/software/minizinc/docs/chi/examples/knapsack.mzn
new file mode 100644
index 0000000..1c6dab3
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/knapsack.mzn
@@ -0,0 +1,13 @@
+enum ITEM;
+int: capacity;
+
+array[ITEM] of int: profits;
+array[ITEM] of int: weights;
+
+var set of ITEM: knapsack;
+
+constraint sum (i in knapsack) (weights[i]) <= capacity;
+
+solve maximize sum (i in knapsack) (profits[i]) ;
+
+output ["knapsack = \(knapsack)\n"];
diff --git a/software/minizinc/docs/chi/examples/laplace.mzn b/software/minizinc/docs/chi/examples/laplace.mzn
new file mode 100644
index 0000000..95f7671
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/laplace.mzn
@@ -0,0 +1,41 @@
+int: w = 4;
+int: h = 4;
+
+% arraydec
+set of int: HEIGHT = 0..h;
+set of int: CHEIGHT = 1..h-1;
+set of int: WIDTH = 0..w;
+set of int: CWIDTH = 1..w-1;
+array[HEIGHT,WIDTH] of var float: t; % 在点(i,j)处的温度
+var float: left; % 左侧温度
+var float: right; % 右侧温度
+var float: top; % 顶部温度
+var float: bottom; % 底部温度
+
+% 拉普拉斯方程:每一个内部点温度是它相邻点的平均值
+constraint forall(i in CHEIGHT, j in CWIDTH)(
+ 4.0*t[i,j] = t[i-1,j] + t[i,j-1] + t[i+1,j] + t[i,j+1]);
+
+% sides
+% 边约束
+constraint forall(i in CHEIGHT)(t[i,0] = left);
+constraint forall(i in CHEIGHT)(t[i,w] = right);
+constraint forall(j in CWIDTH)(t[0,j] = top);
+constraint forall(j in CWIDTH)(t[h,j] = bottom);
+
+% 角约束
+constraint t[0,0]=0.0;
+constraint t[0,w]=0.0;
+constraint t[h,0]=0.0;
+constraint t[h,w]=0.0;
+left = 0.0;
+right = 0.0;
+top = 100.0;
+bottom = 0.0;
+
+solve satisfy;
+
+output [ show_float(6, 2, t[i,j]) ++
+ if j == w then "\n" else " " endif |
+ i in HEIGHT, j in WIDTH
+];
diff --git a/software/minizinc/docs/chi/examples/latin.mzn b/software/minizinc/docs/chi/examples/latin.mzn
new file mode 100644
index 0000000..ec87d7f
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/latin.mzn
@@ -0,0 +1,11 @@
+int: n; % 拉丁方的大小
+array[1..n,1..n] of var 1..n: a;
+
+include "alldifferent.mzn";
+constraint forall(i in 1..n)(
+ alldifferent(j in 1..n)(a[i,j]) /\
+ alldifferent(j in 1..n)(a[j,i])
+ );
+solve satisfy;
+output [ show(a[i,j]) ++ if j == n then "\n" else " " endif |
+ i in 1..n, j in 1..n ];
diff --git a/software/minizinc/docs/chi/examples/latin_squares.mzn b/software/minizinc/docs/chi/examples/latin_squares.mzn
new file mode 100644
index 0000000..1d63993
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/latin_squares.mzn
@@ -0,0 +1,24 @@
+% latin_squares.mzn
+include "globals.mzn";
+
+int: n = 3;
+set of int: N = 1..n;
+array[N, N] of var N: X;
+
+constraint :: "ADRows"
+ forall (i in N)
+ (alldifferent(row(X, i)) :: "AD(row \(i))");
+constraint :: "ADCols"
+ forall (j in N)
+ (alldifferent(col(X, j)) :: "AD(col \(j))");
+
+constraint :: "LLRows"
+ forall (i in 1..n-1)
+ (lex_less(row(X, i), row(X, i+1)) :: "LL(rows \(i) \(i+1))");
+constraint :: "LGCols"
+ forall (j in 1..n-1)
+ (lex_greater(col(X, j), col(X, j+1)) :: "LG(cols \(j) \(j+1)");
+
+solve satisfy;
+
+output [ show2d(X) ];
diff --git a/software/minizinc/docs/chi/examples/latinbool.mzn b/software/minizinc/docs/chi/examples/latinbool.mzn
new file mode 100644
index 0000000..f377e37
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/latinbool.mzn
@@ -0,0 +1,18 @@
+int: n; % 拉丁方的大小
+array[1..n,1..n,1..n] of var bool: a;
+
+predicate atmostone(array[int] of var bool:x) =
+ forall(i,j in index_set(x) where i < j)(
+ (not x[i] \/ not x[j]));
+predicate exactlyone(array[int] of var bool:x) =
+ atmostone(x) /\ exists(x);
+
+constraint forall(i,j in 1..n)(
+ exactlyone(k in 1..n)(a[i,j,k]) /\
+ exactlyone(k in 1..n)(a[i,k,j]) /\
+ exactlyone(k in 1..n)(a[k,i,j])
+ );
+solve satisfy;
+output [ if fix(a[i,j,k]) then
+ show(k) ++ if j == n then "\n" else " " endif
+ else "" endif | i,j,k in 1..n ];
diff --git a/software/minizinc/docs/chi/examples/layout.dzn b/software/minizinc/docs/chi/examples/layout.dzn
new file mode 100644
index 0000000..2aed076
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/layout.dzn
@@ -0,0 +1,9 @@
+pixelwidth = 100;
+maxlines = 9;
+
+rows = 3;
+cols = 3;
+
+sizes = [| [60,35,24], [70,43,30,20], [30,20,15]
+ | [70,43,30,20], [30,20,15], [15]
+ | [60,35,24], [70,43,30,20], [30,18,12] |];
diff --git a/software/minizinc/docs/chi/examples/lightup.dzn b/software/minizinc/docs/chi/examples/lightup.dzn
new file mode 100644
index 0000000..0e4b4ac
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/lightup.dzn
@@ -0,0 +1,9 @@
+h = 7;
+w = 7;
+b = [| -1,-1,-1,-1, 0,-1,-1
+ | -1,-1,-1,-1,-1,-1,-1
+ | 0,-1,-1, 3,-1,-1,-1
+ | -1,-1, 2,-1, 4,-1,-1
+ | -1,-1,-1, 5,-1,-1, 1
+ | -1,-1,-1,-1,-1,-1,-1
+ | 1,-1, 2,-1,-1,-1,-1 |];
diff --git a/software/minizinc/docs/chi/examples/lightup.mzn b/software/minizinc/docs/chi/examples/lightup.mzn
new file mode 100644
index 0000000..c473583
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/lightup.mzn
@@ -0,0 +1,39 @@
+int: h; set of int: H = 1..h; % 板高度
+int: w; set of int: W = 1..w; % 板宽度
+array[H,W] of -1..5: b; % 板
+int: E = -1; % 空白格
+set of int: N = 0..4; % 填充并含有数字的网格
+int: F = 5; % 填充但不含有数字的网格
+
+% 位置 (i1,j1) 对位置 (i2,j2) 可见
+test visible(int: i1, int: j1, int: i2, int: j2) =
+ ((i1 == i2) /\ forall(j in min(j1,j2)..max(j1,j2))(b[i1,j] == E))
+ \/ ((j1 == j2) /\ forall(i in min(i1,i2)..max(i1,i2))(b[i,j1] == E));
+
+array[H,W] of var bool: l; % is there a light
+
+% 填充的网格没有灯泡
+constraint forall(i in H, j in W where b[i,j] != E)(l[i,j] == false);
+% lights next to filled numbered square agree
+
+constraint forall(i in H, j in W where b[i,j] in N)(
+ bool_sum_eq([ l[i1,j1] | i1 in i-1..i+1, j1 in j-1..j+1 where
+ abs(i1 - i) + abs(j1 - j) == 1 /\
+ i1 in H /\ j1 in W ], b[i,j]));
+% 每个空白网格是被照亮的
+constraint forall(i in H, j in W where b[i,j] == E)(
+ exists(j1 in W where visible(i,j,i,j1))(l[i,j1]) \/
+ exists(i1 in H where visible(i,j,i1,j))(l[i1,j])
+ );
+% 任何两个灯泡看不到彼此
+constraint forall(i1,i2 in H, j1,j2 in W where
+ (i1 != i2 \/ j1 != j2) /\ b[i1,j1] == E
+ /\ b[i2,j2] == E /\ visible(i1,j1,i2,j2))(
+ not l[i1,j1] \/ not l[i2,j2]
+ );
+
+solve satisfy;
+output [ if b[i,j] != E then show(b[i,j])
+ else if fix(l[i,j]) then "L" else "." endif
+ endif ++ if j == w then "\n" else " " endif |
+ i in H, j in W];
diff --git a/software/minizinc/docs/chi/examples/linear.mzn b/software/minizinc/docs/chi/examples/linear.mzn
new file mode 100644
index 0000000..2b30a63
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/linear.mzn
@@ -0,0 +1,6 @@
+int: d = -1;
+var 0..10: x;
+var -3..6: y;
+var 3..8: z;
+constraint 3*x - y + x * z <= 19 + d * (x + y + z) - 4*d;
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/loan.mzn b/software/minizinc/docs/chi/examples/loan.mzn
new file mode 100644
index 0000000..7875902
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/loan.mzn
@@ -0,0 +1,23 @@
+% 变量
+var float: R; % 季度还款
+var float: P; % 初始借贷本金
+var 0.0 .. 10.0: I; % 利率
+
+% 中间变量
+var float: B1; % 一个季度后的欠款
+var float: B2; % 两个季度后的欠款
+var float: B3; % 三个季度后的欠款
+var float: B4; % 最后欠款
+
+constraint B1 = P * (1.0 + I) - R;
+constraint B2 = B1 * (1.0 + I) - R;
+constraint B3 = B2 * (1.0 + I) - R;
+constraint B4 = B3 * (1.0 + I) - R;
+
+solve satisfy;
+
+output [
+ "Borrowing ", show_float(0, 2, P), " at ", show(I*100.0),
+ "% interest, and repaying ", show_float(0, 2, R),
+ "\nper quarter for 1 year leaves ", show_float(0, 2, B4), " owing\n"
+];
diff --git a/software/minizinc/docs/chi/examples/loan1.dzn b/software/minizinc/docs/chi/examples/loan1.dzn
new file mode 100644
index 0000000..d5fd9da
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/loan1.dzn
@@ -0,0 +1,3 @@
+I = 0.04;
+P = 1000.0;
+R = 260.0;
diff --git a/software/minizinc/docs/chi/examples/loan2.dzn b/software/minizinc/docs/chi/examples/loan2.dzn
new file mode 100644
index 0000000..e39fb72
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/loan2.dzn
@@ -0,0 +1,3 @@
+I = 0.04;
+P = 1000.0;
+B4 = 0.0;
diff --git a/software/minizinc/docs/chi/examples/loan3.dzn b/software/minizinc/docs/chi/examples/loan3.dzn
new file mode 100644
index 0000000..ef2762a
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/loan3.dzn
@@ -0,0 +1,3 @@
+I = 0.04;
+R = 250.0;
+B4 = 0.0;
diff --git a/software/minizinc/docs/chi/examples/magic-series.mzn b/software/minizinc/docs/chi/examples/magic-series.mzn
new file mode 100644
index 0000000..30a8e68
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/magic-series.mzn
@@ -0,0 +1,9 @@
+int: n;
+array[0..n-1] of var 0..n: s;
+
+constraint forall(i in 0..n-1) (
+ s[i] = (sum(j in 0..n-1)(bool2int(s[j]=i))));
+
+solve satisfy;
+
+output [ "s = \(s);\n" ] ;
diff --git a/software/minizinc/docs/chi/examples/magic-series2.mzn b/software/minizinc/docs/chi/examples/magic-series2.mzn
new file mode 100644
index 0000000..654c3f0
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/magic-series2.mzn
@@ -0,0 +1,11 @@
+int: n;
+array[0..n-1] of var 0..n: s;
+
+constraint forall(i in 0..n-1) (
+ s[i] = (sum(j in 0..n-1)(bool2int(s[j]=i))));
+% redundant
+constraint sum(i in 0..n-1)(s[i]) = n;
+constraint sum(i in 0..n-1)(s[i] * i) = n;
+solve satisfy;
+
+output [ "s = ", show(s), ";\n" ] ;
diff --git a/software/minizinc/docs/chi/examples/manhattan.mzn b/software/minizinc/docs/chi/examples/manhattan.mzn
new file mode 100644
index 0000000..5570bbf
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/manhattan.mzn
@@ -0,0 +1,31 @@
+int: n;
+set of int: NUM = 1..n;
+
+array[NUM] of var NUM: x;
+array[NUM] of var NUM: y;
+array[NUM,NUM] of var 0..2*n-2: dist =
+ array2d(NUM,NUM,[
+ if i < j then manhattan(x[i],y[i],x[j],y[j]) else 0 endif
+ | i,j in NUM ]);
+
+% manf
+function var int: manhattan(var int: x1, var int: y1,
+ var int: x2, var int: y2) =
+ abs(x1 - x2) + abs(y1 - y2);
+
+constraint forall(i,j in NUM where i < j)
+ (dist[i,j] >= max(i,j)-1);
+
+var int: obj = sum(i,j in NUM where i < j)(dist[i,j]);
+solve minimize obj;
+
+% 简单地显示结果
+include "alldifferent_except_0.mzn";
+array[NUM,NUM] of var 0..n: grid;
+constraint forall(i in NUM)(grid[x[i],y[i]] = i);
+constraint alldifferent_except_0([grid[i,j] | i,j in NUM]);
+
+output ["obj = \(obj);\n"] ++
+ [ if fix(grid[i,j]) > 0 then show(grid[i,j]) else "." endif
+ ++ if j = n then "\n" else "" endif
+ | i,j in NUM ];
diff --git a/software/minizinc/docs/chi/examples/meal-zinc.dzn b/software/minizinc/docs/chi/examples/meal-zinc.dzn
new file mode 100644
index 0000000..1c010ab
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/meal-zinc.dzn
@@ -0,0 +1,22 @@
+enum Name = { icecream, banana, chocolate_cake, lasagna,
+ steak, rice, chips, brocolli, beans };
+
+meal_items = { (icecream, 1200, 50, 10, 120, 400),
+ (banana, 800, 120, 5, 20, 120),
+ (chocolate_cake, 2500, 400, 20, 100, 600),
+ (lasagna, 3000, 200, 100, 250, 450),
+ (steak, 1800, 800, 50, 100, 1200),
+ (rice, 1200, 50, 5, 20, 100),
+ (chips, 2000, 50, 200, 200, 250),
+ (brocolli, 700, 100, 10, 10, 125),
+ (beans, 1900, 250, 60, 90, 150) };
+
+min_energy = 3300;
+min_protein = 500;
+
+max_salt = 180;
+max_fat = 320;
+
+desserts = { icecream, banana, chocolate_cake };
+mains = { lasagna, steak, beans };
+sides = { rice, chips, brocolli };
diff --git a/software/minizinc/docs/chi/examples/meal.dzn b/software/minizinc/docs/chi/examples/meal.dzn
new file mode 100644
index 0000000..c57be5a
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/meal.dzn
@@ -0,0 +1,20 @@
+FOOD = { icecream, banana, chocolatecake, lasagna,
+ steak, rice, chips, brocolli, beans} ;
+
+dd = [| icecream, 1200, 50, 10, 120, 400 % 冰淇淋
+ | banana, 800, 120, 5, 20, 120 % 香蕉
+ | chocolatecake, 2500, 400, 20, 100, 600 % 巧克力蛋糕
+ | lasagna, 3000, 200, 100, 250, 450 % 千层面
+ | steak, 1800, 800, 50, 100, 1200 % 牛排
+ | rice, 1200, 50, 5, 20, 100 % 米饭
+ | chips, 2000, 50, 200, 200, 250 % 薯条
+ | brocolli, 700, 100, 10, 10, 125 % 花椰菜
+ | beans, 1900, 250, 60, 90, 150 |]; % 黄豆
+
+min_energy = 3300;
+min_protein = 500;
+max_salt = 180;
+max_fat = 320;
+desserts = { icecream, banana, chocolatecake };
+mains = { lasagna, steak, rice };
+sides = { chips, brocolli, beans };
diff --git a/software/minizinc/docs/chi/examples/meal.mzn b/software/minizinc/docs/chi/examples/meal.mzn
new file mode 100644
index 0000000..674cc81
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/meal.mzn
@@ -0,0 +1,36 @@
+% 规划均衡的膳食
+include "table.mzn";
+int: min_energy;
+int: min_protein;
+int: max_salt;
+int: max_fat;
+set of FOOD: desserts;
+set of FOOD: mains;
+set of FOOD: sides;
+enum FEATURE = { name, energy, protein, salt, fat, cost};
+enum FOOD;
+array[FOOD,FEATURE] of int: dd; % 食物数据库
+
+array[FEATURE] of var int: main;
+array[FEATURE] of var int: side;
+array[FEATURE] of var int: dessert;
+var int: budget;
+
+constraint main[name] in mains;
+constraint side[name] in sides;
+constraint dessert[name] in desserts;
+constraint table(main, dd);
+constraint table(side, dd);
+constraint table(dessert, dd);
+constraint main[energy] + side[energy] + dessert[energy] >=min_energy;
+constraint main[protein]+side[protein]+dessert[protein] >=min_protein;
+constraint main[salt] + side[salt] + dessert[salt] <= max_salt;
+constraint main[fat] + side[fat] + dessert[fat] <= max_fat;
+constraint budget = main[cost] + side[cost] + dessert[cost];
+
+solve minimize budget;
+
+output ["main = ",show(to_enum(FOOD,main[name])),
+ ", side = ",show(to_enum(FOOD,side[name])),
+ ", dessert = ",show(to_enum(FOOD,dessert[name])),
+ ", cost = ",show(budget), "\n"];
diff --git a/software/minizinc/docs/chi/examples/moving.dzn b/software/minizinc/docs/chi/examples/moving.dzn
new file mode 100644
index 0000000..da802f2
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/moving.dzn
@@ -0,0 +1,10 @@
+OBJECTS = { piano, fridge, doublebed, singlebed,
+ wardrobe, chair1, chair2, table };
+
+duration = [60, 45, 30, 30, 20, 15, 15, 15];
+handlers = [3, 2, 2, 1, 2, 1, 1, 2];
+trolleys = [2, 1, 2, 2, 2, 0, 0, 1];
+
+available_time = 180;
+available_handlers = 4;
+available_trolleys = 3;
diff --git a/software/minizinc/docs/chi/examples/moving.mzn b/software/minizinc/docs/chi/examples/moving.mzn
new file mode 100644
index 0000000..53d3a6b
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/moving.mzn
@@ -0,0 +1,22 @@
+include "cumulative.mzn";
+
+enum OBJECTS;
+array[OBJECTS] of int: duration; % 移动的持续时间
+array[OBJECTS] of int: handlers; % 需要的搬运工的数量
+array[OBJECTS] of int: trolleys; % 需要的手推车的数量
+
+int: available_handlers;
+int: available_trolleys;
+int: available_time;
+
+array[OBJECTS] of var 0..available_time: start;
+var 0..available_time: end;
+
+constraint cumulative(start, duration, handlers, available_handlers);
+constraint cumulative(start, duration, trolleys, available_trolleys);
+
+constraint forall(o in OBJECTS)(start[o] +duration[o] <= end);
+
+solve minimize end;
+
+output [ "start = \(start)\nend = \(end)\n"];
diff --git a/software/minizinc/docs/chi/examples/nqueens-ann.mzn b/software/minizinc/docs/chi/examples/nqueens-ann.mzn
new file mode 100644
index 0000000..1fbdd3e
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/nqueens-ann.mzn
@@ -0,0 +1,17 @@
+annotation bitdomain(int:nwords);
+
+include "alldifferent.mzn";
+
+int: n;
+array [1..n] of var 1..n: q :: bitdomain(n div 32);
+
+constraint alldifferent(q) :: domain;
+constraint alldifferent([ q[i] + i | i in 1..n]) :: domain;
+constraint alldifferent([ q[i] - i | i in 1..n]) :: domain;
+
+ann: search_ann;
+
+solve :: search_ann satisfy;
+
+output [ if fix(q[j]) == i then "Q" else "." endif ++
+ if j == n then "\n" else "" endif | i,j in 1..n]
diff --git a/software/minizinc/docs/chi/examples/nqueens.mzn b/software/minizinc/docs/chi/examples/nqueens.mzn
new file mode 100644
index 0000000..6eb45a7
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/nqueens.mzn
@@ -0,0 +1,14 @@
+int: n;
+array [1..n] of var 1..n: q; % i列的皇后在行q[i]
+
+include "alldifferent.mzn";
+
+constraint alldifferent(q); % 不同行
+constraint alldifferent([ q[i] + i | i in 1..n]); % 不同对角线
+constraint alldifferent([ q[i] - i | i in 1..n]); % 上+下
+
+% 搜索
+solve :: int_search(q, first_fail, indomain_min, complete)
+ satisfy;
+output [ if fix(q[j]) == i then "Q" else "." endif ++
+ if j == n then "\n" else "" endif | i,j in 1..n]
diff --git a/software/minizinc/docs/chi/examples/nqueens_sym.mzn b/software/minizinc/docs/chi/examples/nqueens_sym.mzn
new file mode 100644
index 0000000..eddd9f5
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/nqueens_sym.mzn
@@ -0,0 +1,34 @@
+int: n;
+array [1..n] of var 1..n: q; % 在第i列的皇后在q[i]上
+
+include "alldifferent.mzn";
+
+constraint alldifferent(q); % distinct rows
+constraint alldifferent([ q[i] + i | i in 1..n]); % distinct diagonals
+constraint alldifferent([ q[i] - i | i in 1..n]); % upwards+downwards
+
+include "lex_lesseq.mzn";
+
+% 可选的布尔模型:
+% 映射每一个位置 i,j到一个布尔变量上来表示在i,j上是否有一个皇后
+array[1..n,1..n] of var bool: qb;
+
+% 连通约束
+constraint forall (i,j in 1..n) ( qb[i,j] <-> (q[i]=j) );
+
+% 字典排序对称性破缺
+constraint
+ lex_lesseq(array1d(qb), [ qb[j,i] | i,j in 1..n ])
+/\ lex_lesseq(array1d(qb), [ qb[i,j] | i in reverse(1..n), j in 1..n ])
+/\ lex_lesseq(array1d(qb), [ qb[j,i] | i in 1..n, j in reverse(1..n) ])
+/\ lex_lesseq(array1d(qb), [ qb[i,j] | i in 1..n, j in reverse(1..n) ])
+/\ lex_lesseq(array1d(qb), [ qb[j,i] | i in reverse(1..n), j in 1..n ])
+/\ lex_lesseq(array1d(qb), [ qb[i,j] | i,j in reverse(1..n) ])
+/\ lex_lesseq(array1d(qb), [ qb[j,i] | i,j in reverse(1..n) ])
+;
+
+% 搜索
+solve :: int_search(q, first_fail, indomain_min, complete)
+ satisfy;
+output [ if fix(q[j]) == i then "Q" else "." endif ++
+ if j == n then "\n" else "" endif | i,j in 1..n]
diff --git a/software/minizinc/docs/chi/examples/nurse.mzn b/software/minizinc/docs/chi/examples/nurse.mzn
new file mode 100644
index 0000000..2d2ae0d
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/nurse.mzn
@@ -0,0 +1,35 @@
+% 简单护士排班问题
+include "regular.mzn";
+enum NURSE;
+enum DAY;
+int: req_day;
+int: req_night;
+int: min_night;
+
+enum SHIFT = { d, n, o };
+int: S = card(SHIFT);
+
+int: Q = 6; int: q0 = 1; set of int: STATE = 1..Q;
+array[STATE,SHIFT] of int: t =
+ [| 2, 3, 1 % 状态1
+ | 4, 4, 1 % 状态2
+ | 4, 5, 1 % 状态3
+ | 6, 6, 1 % 状态4
+ | 6, 0, 1 % 状态5
+ | 0, 0, 1|]; % 状态6
+
+array[NURSE,DAY] of var SHIFT: roster;
+
+constraint forall(j in DAY)(
+ sum(i in NURSE)(roster[i,j] == d) == req_day /\
+ sum(i in NURSE)(roster[i,j] == n) == req_night
+ );
+constraint forall(i in NURSE)(
+ regular([roster[i,j] | j in DAY], Q, S, t, q0, STATE) /\
+ sum(j in DAY)(roster[i,j] == n) >= min_night
+ );
+
+solve satisfy;
+
+output [ show(roster[i,j]) ++ if j==card(DAY) then "\n" else " " endif
+ | i in NURSE, j in DAY ];
diff --git a/software/minizinc/docs/chi/examples/oesort.mzn b/software/minizinc/docs/chi/examples/oesort.mzn
new file mode 100644
index 0000000..2f1f542
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/oesort.mzn
@@ -0,0 +1,39 @@
+%% 奇偶排序
+%% y是x的有序版本,所有的真都在假之前
+predicate oesort(array[int] of var bool:x, array[int] of var bool:y)=
+ let { int: c = card(index_set(x)) } in
+ if c == 1 then x[1] == y[1]
+ elseif c == 2 then comparator(x[1],x[2],y[1],y[2])
+ else
+ let {
+ array[1..c div 2] of var bool:xf = [x[i] | i in 1..c div 2],
+ array[1..c div 2] of var bool:xl = [x[i] | i in c div 2 +1..c],
+ array[1..c div 2] of var bool:tf,
+ array[1..c div 2] of var bool:tl } in
+ oesort(xf,tf) /\ oesort(xl,tl) /\ oemerge(tf ++ tl, y)
+ endif;
+
+%% 奇偶合并
+%% y 是 x的有序版本,所有的真都在假之前
+%% 假设 x的前一半是有序的,后一半也是
+predicate oemerge(array[int] of var bool:x, array[int] of var bool:y)=
+ let { int: c = card(index_set(x)) } in
+ if c == 1 then x[1] == y[1]
+ elseif c == 2 then comparator(x[1],x[2],y[1],y[2])
+ else
+ let { array[1..c div 2] of var bool:xo =
+ [ x[i] | i in 1..c where i mod 2 == 1],
+ array[1..c div 2] of var bool:xe =
+ [ x[i] | i in 1..c where i mod 2 == 0],
+ array[1..c div 2] of var bool:to,
+ array[1..c div 2] of var bool:te } in
+ oemerge(xo,to) /\ oemerge(xe,te) /\
+ y[1] = to[1] /\
+ forall(i in 1..c div 2 -1)(
+ comparator(te[i],to[i+1],y[2*i],y[2*i+1])) /\
+ y[c] = te[c div 2]
+ endif;
+
+% 比较器 o1 = max(i1,i2), o2 = min(i1,i2)
+predicate comparator(var bool:i1,var bool:i2,var bool:o1,var bool:o2)=
+ (o1 = (i1 \/ i2)) /\ (o2 = (i1 /\ i2));
diff --git a/software/minizinc/docs/chi/examples/pantry.dzn b/software/minizinc/docs/chi/examples/pantry.dzn
new file mode 100644
index 0000000..7b9dd9b
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/pantry.dzn
@@ -0,0 +1,5 @@
+flour = 4000;
+banana = 6;
+sugar = 2000;
+butter = 500;
+cocoa = 500;
diff --git a/software/minizinc/docs/chi/examples/pantry2.dzn b/software/minizinc/docs/chi/examples/pantry2.dzn
new file mode 100644
index 0000000..1b81d81
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/pantry2.dzn
@@ -0,0 +1,5 @@
+flour = 8000;
+banana = 11;
+sugar = 3000;
+butter = 1500;
+cocoa = 800;
diff --git a/software/minizinc/docs/chi/examples/reflection.mzn b/software/minizinc/docs/chi/examples/reflection.mzn
new file mode 100644
index 0000000..890abe7
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/reflection.mzn
@@ -0,0 +1,6 @@
+var -10..10: x;
+constraint x in 0..4;
+int: y = lb(x);
+set of int: D = dom(x);
+solve satisfy;
+output ["y = ", show(y), "\nD = ", show(D), "\n"];
diff --git a/software/minizinc/docs/chi/examples/scope.mzn b/software/minizinc/docs/chi/examples/scope.mzn
new file mode 100644
index 0000000..f61823e
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/scope.mzn
@@ -0,0 +1,7 @@
+int: x = 3;
+int: y = 4;
+predicate smallx(var int:y) = -x <= y /\ y <= x;
+predicate p(int: u, var bool: y) =
+ exists(x in 1..u)(y \/ smallx(x));
+constraint p(x,false);
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/send-more-money.mzn b/software/minizinc/docs/chi/examples/send-more-money.mzn
new file mode 100644
index 0000000..8260eba
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/send-more-money.mzn
@@ -0,0 +1,22 @@
+include "alldifferent.mzn";
+
+var 1..9: S;
+var 0..9: E;
+var 0..9: N;
+var 0..9: D;
+var 1..9: M;
+var 0..9: O;
+var 0..9: R;
+var 0..9: Y;
+
+constraint 1000 * S + 100 * E + 10 * N + D
+ + 1000 * M + 100 * O + 10 * R + E
+ = 10000 * M + 1000 * O + 100 * N + 10 * E + Y;
+
+constraint alldifferent([S,E,N,D,M,O,R,Y]);
+
+solve satisfy;
+
+output [" \(S)\(E)\(N)\(D)\n",
+ "+ \(M)\(O)\(R)\(E)\n",
+ "= \(M)\(O)\(N)\(E)\(Y)\n"];
diff --git a/software/minizinc/docs/chi/examples/simple-prod-planning-data.dzn b/software/minizinc/docs/chi/examples/simple-prod-planning-data.dzn
new file mode 100644
index 0000000..eb54563
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/simple-prod-planning-data.dzn
@@ -0,0 +1,9 @@
+% 简单批量生产计划模型的数据文件
+Products = { BananaCake, ChocolateCake };
+profit = [400, 450]; % 以分为单位
+
+Resources = { Flour, Banana, Sugar, Butter, Cocoa };
+capacity = [4000, 6, 2000, 500, 500];
+
+consumption= [| 250, 2, 75, 100, 0,
+ | 200, 0, 150, 150, 75 |];
diff --git a/software/minizinc/docs/chi/examples/simple-prod-planning.mzn b/software/minizinc/docs/chi/examples/simple-prod-planning.mzn
new file mode 100644
index 0000000..a224fb1
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/simple-prod-planning.mzn
@@ -0,0 +1,36 @@
+% 要制造的产品
+enum Products;
+% 每种产品的单位利润
+array[Products] of int: profit;
+% 用到的资源
+enum Resources;
+% 每种资源可获得的数量
+array[Resources] of int: capacity;
+
+% 制造一个单位的产品需要的资源单位量
+array[Products, Resources] of int: consumption;
+constraint assert(forall (r in Resources, p in Products)
+ (consumption[p,r] >= 0), "Error: negative consumption");
+
+% 产品数量的界
+int: mproducts = max (p in Products)
+ (min (r in Resources where consumption[p,r] > 0)
+ (capacity[r] div consumption[p,r]));
+
+% 变量:每种产品我们需要制造多少
+array[Products] of var 0..mproducts: produce;
+array[Resources] of var 0..max(capacity): used;
+
+% 产量不可以使用超过可获得的资源量:
+constraint forall (r in Resources) (
+ used[r] = sum (p in Products)(consumption[p, r] * produce[p])
+);
+constraint forall (r in Resources) (
+ used[r] <= capacity[r]
+);
+
+% 最大化利润
+solve maximize sum (p in Products) (profit[p]*produce[p]);
+
+output [ "\(p) = \(produce[p]);\n" | p in Products ] ++
+ [ "\(r) = \(used[r]);\n" | r in Resources ];
diff --git a/software/minizinc/docs/chi/examples/social-golfers.dzn b/software/minizinc/docs/chi/examples/social-golfers.dzn
new file mode 100644
index 0000000..50d8a79
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/social-golfers.dzn
@@ -0,0 +1,3 @@
+weeks = 4;
+groups = 4;
+size =3 ;
diff --git a/software/minizinc/docs/chi/examples/social-golfers.fzn b/software/minizinc/docs/chi/examples/social-golfers.fzn
new file mode 100644
index 0000000..e3a55a1
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/social-golfers.fzn
@@ -0,0 +1,653 @@
+predicate array_set_partition(array [int] of var set of int: S,set of int: universe);
+var set of 1..12: X_INTRODUCED_0;
+var set of 1..12: X_INTRODUCED_1;
+var set of 1..12: X_INTRODUCED_2;
+var set of 1..12: X_INTRODUCED_3;
+var set of 1..12: X_INTRODUCED_4;
+var set of 1..12: X_INTRODUCED_5;
+var set of 1..12: X_INTRODUCED_6;
+var set of 1..12: X_INTRODUCED_7;
+var set of 1..12: X_INTRODUCED_8;
+var set of 1..12: X_INTRODUCED_9;
+var set of 1..12: X_INTRODUCED_10;
+var set of 1..12: X_INTRODUCED_11;
+var set of 1..12: X_INTRODUCED_12;
+var set of 1..12: X_INTRODUCED_13;
+var set of 1..12: X_INTRODUCED_14;
+var set of 1..12: X_INTRODUCED_15;
+var set of 1..12: X_INTRODUCED_16 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_17 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_18 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_19 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_20 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_21 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_22 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_23 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_24 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_25 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_26 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_27 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_28 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_29 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_30 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_31 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_32 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_33 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_34 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_35 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_36 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_37 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_38 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_39 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_40 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_41 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_42 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_43 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_44 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_45 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_46 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_47 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_48 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_49 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_50 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_51 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_52 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_53 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_54 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_55 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_56 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_57 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_58 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_59 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_60 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_61 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_62 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_63 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_64 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_65 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_66 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_67 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_68 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_69 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_70 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_71 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_72 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_73 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_74 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_75 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_76 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_77 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_78 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_79 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_80 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_81 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_82 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_83 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_84 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_85 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_86 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_87 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_88 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_89 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_90 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_91 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_92 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_93 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_94 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_95 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_96 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_97 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_98 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_99 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_100 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_101 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_102 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_103 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_104 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_105 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_106 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_107 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_108 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_109 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_110 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_111 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_112 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_113 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_114 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_115 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_116 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_117 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_118 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_119 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_120 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_121 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_122 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_123 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_124 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_125 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_126 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_127 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_128 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_129 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_130 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_131 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_132 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_133 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_134 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_135 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_136 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_137 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_138 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_139 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_140 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_141 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_142 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_143 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_144 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_145 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_146 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_147 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_148 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_149 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_150 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_151 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_152 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_153 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_154 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_155 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_156 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_157 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_158 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_159 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_160 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_161 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_162 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_163 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_164 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_165 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_166 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_167 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_168 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_169 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_170 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_171 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_172 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_173 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_174 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_175 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_176 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_177 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_178 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_179 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_180 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_181 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_182 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_183 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_184 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_185 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_186 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_187 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_188 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_189 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_190 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_191 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_192 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_193 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_194 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_195 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_196 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_197 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_198 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_199 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_200 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_201 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_202 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_203 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_204 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_205 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_206 ::var_is_introduced :: is_defined_var;
+var 0..1: X_INTRODUCED_207 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_212 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_213 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_214 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_215 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_216 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_217 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_218 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_219 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_220 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_221 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_222 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_223 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_224 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_225 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_226 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_227 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_228 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_229 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_230 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_231 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_232 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_233 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_234 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_235 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_236 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_237 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_238 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_239 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_240 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_241 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_242 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_243 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_244 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_245 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_246 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_247 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_248 ::var_is_introduced :: is_defined_var;
+var set of 1..12: X_INTRODUCED_249 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_250 ::var_is_introduced :: is_defined_var;
+var 0..12: X_INTRODUCED_251 ::var_is_introduced :: is_defined_var;
+array [1..16] of var set of int: Sched:: output_array([1..4,1..4]) = [X_INTRODUCED_0,X_INTRODUCED_1,X_INTRODUCED_2,X_INTRODUCED_3,X_INTRODUCED_4,X_INTRODUCED_5,X_INTRODUCED_6,X_INTRODUCED_7,X_INTRODUCED_8,X_INTRODUCED_9,X_INTRODUCED_10,X_INTRODUCED_11,X_INTRODUCED_12,X_INTRODUCED_13,X_INTRODUCED_14,X_INTRODUCED_15];
+array [1..4] of var set of int: X_INTRODUCED_208 ::var_is_introduced = [X_INTRODUCED_0,X_INTRODUCED_1,X_INTRODUCED_2,X_INTRODUCED_3];
+array [1..4] of var set of int: X_INTRODUCED_209 ::var_is_introduced = [X_INTRODUCED_4,X_INTRODUCED_5,X_INTRODUCED_6,X_INTRODUCED_7];
+array [1..4] of var set of int: X_INTRODUCED_210 ::var_is_introduced = [X_INTRODUCED_8,X_INTRODUCED_9,X_INTRODUCED_10,X_INTRODUCED_11];
+array [1..4] of var set of int: X_INTRODUCED_211 ::var_is_introduced = [X_INTRODUCED_12,X_INTRODUCED_13,X_INTRODUCED_14,X_INTRODUCED_15];
+constraint int_le(X_INTRODUCED_17,1);
+constraint int_le(X_INTRODUCED_19,1);
+constraint int_le(X_INTRODUCED_21,1);
+constraint int_le(X_INTRODUCED_23,1);
+constraint int_le(X_INTRODUCED_25,1);
+constraint int_le(X_INTRODUCED_27,1);
+constraint int_le(X_INTRODUCED_29,1);
+constraint int_le(X_INTRODUCED_31,1);
+constraint int_le(X_INTRODUCED_33,1);
+constraint int_le(X_INTRODUCED_35,1);
+constraint int_le(X_INTRODUCED_37,1);
+constraint int_le(X_INTRODUCED_39,1);
+constraint int_le(X_INTRODUCED_41,1);
+constraint int_le(X_INTRODUCED_43,1);
+constraint int_le(X_INTRODUCED_45,1);
+constraint int_le(X_INTRODUCED_47,1);
+constraint int_le(X_INTRODUCED_49,1);
+constraint int_le(X_INTRODUCED_51,1);
+constraint int_le(X_INTRODUCED_53,1);
+constraint int_le(X_INTRODUCED_55,1);
+constraint int_le(X_INTRODUCED_57,1);
+constraint int_le(X_INTRODUCED_59,1);
+constraint int_le(X_INTRODUCED_61,1);
+constraint int_le(X_INTRODUCED_63,1);
+constraint int_le(X_INTRODUCED_65,1);
+constraint int_le(X_INTRODUCED_67,1);
+constraint int_le(X_INTRODUCED_69,1);
+constraint int_le(X_INTRODUCED_71,1);
+constraint int_le(X_INTRODUCED_73,1);
+constraint int_le(X_INTRODUCED_75,1);
+constraint int_le(X_INTRODUCED_77,1);
+constraint int_le(X_INTRODUCED_79,1);
+constraint int_le(X_INTRODUCED_81,1);
+constraint int_le(X_INTRODUCED_83,1);
+constraint int_le(X_INTRODUCED_85,1);
+constraint int_le(X_INTRODUCED_87,1);
+constraint int_le(X_INTRODUCED_89,1);
+constraint int_le(X_INTRODUCED_91,1);
+constraint int_le(X_INTRODUCED_93,1);
+constraint int_le(X_INTRODUCED_95,1);
+constraint int_le(X_INTRODUCED_97,1);
+constraint int_le(X_INTRODUCED_99,1);
+constraint int_le(X_INTRODUCED_101,1);
+constraint int_le(X_INTRODUCED_103,1);
+constraint int_le(X_INTRODUCED_105,1);
+constraint int_le(X_INTRODUCED_107,1);
+constraint int_le(X_INTRODUCED_109,1);
+constraint int_le(X_INTRODUCED_111,1);
+constraint int_le(X_INTRODUCED_113,1);
+constraint int_le(X_INTRODUCED_115,1);
+constraint int_le(X_INTRODUCED_117,1);
+constraint int_le(X_INTRODUCED_119,1);
+constraint int_le(X_INTRODUCED_121,1);
+constraint int_le(X_INTRODUCED_123,1);
+constraint int_le(X_INTRODUCED_125,1);
+constraint int_le(X_INTRODUCED_127,1);
+constraint int_le(X_INTRODUCED_129,1);
+constraint int_le(X_INTRODUCED_131,1);
+constraint int_le(X_INTRODUCED_133,1);
+constraint int_le(X_INTRODUCED_135,1);
+constraint int_le(X_INTRODUCED_137,1);
+constraint int_le(X_INTRODUCED_139,1);
+constraint int_le(X_INTRODUCED_141,1);
+constraint int_le(X_INTRODUCED_143,1);
+constraint int_le(X_INTRODUCED_145,1);
+constraint int_le(X_INTRODUCED_147,1);
+constraint int_le(X_INTRODUCED_149,1);
+constraint int_le(X_INTRODUCED_151,1);
+constraint int_le(X_INTRODUCED_153,1);
+constraint int_le(X_INTRODUCED_155,1);
+constraint int_le(X_INTRODUCED_157,1);
+constraint int_le(X_INTRODUCED_159,1);
+constraint int_le(X_INTRODUCED_161,1);
+constraint int_le(X_INTRODUCED_163,1);
+constraint int_le(X_INTRODUCED_165,1);
+constraint int_le(X_INTRODUCED_167,1);
+constraint int_le(X_INTRODUCED_169,1);
+constraint int_le(X_INTRODUCED_171,1);
+constraint int_le(X_INTRODUCED_173,1);
+constraint int_le(X_INTRODUCED_175,1);
+constraint int_le(X_INTRODUCED_177,1);
+constraint int_le(X_INTRODUCED_179,1);
+constraint int_le(X_INTRODUCED_181,1);
+constraint int_le(X_INTRODUCED_183,1);
+constraint int_le(X_INTRODUCED_185,1);
+constraint int_le(X_INTRODUCED_187,1);
+constraint int_le(X_INTRODUCED_189,1);
+constraint int_le(X_INTRODUCED_191,1);
+constraint int_le(X_INTRODUCED_193,1);
+constraint int_le(X_INTRODUCED_195,1);
+constraint int_le(X_INTRODUCED_197,1);
+constraint int_le(X_INTRODUCED_199,1);
+constraint int_le(X_INTRODUCED_201,1);
+constraint int_le(X_INTRODUCED_203,1);
+constraint int_le(X_INTRODUCED_205,1);
+constraint int_le(X_INTRODUCED_207,1);
+constraint array_set_partition(X_INTRODUCED_208,1..12);
+constraint array_set_partition(X_INTRODUCED_209,1..12);
+constraint array_set_partition(X_INTRODUCED_210,1..12);
+constraint array_set_partition(X_INTRODUCED_211,1..12);
+constraint set_eq(X_INTRODUCED_212,1..0);
+constraint set_eq(X_INTRODUCED_213,1..0);
+constraint set_eq(X_INTRODUCED_214,1..0);
+constraint int_eq(X_INTRODUCED_215,3);
+constraint set_eq(X_INTRODUCED_216,1..0);
+constraint set_eq(X_INTRODUCED_217,1..0);
+constraint int_eq(X_INTRODUCED_218,3);
+constraint set_eq(X_INTRODUCED_219,1..0);
+constraint int_eq(X_INTRODUCED_220,3);
+constraint int_eq(X_INTRODUCED_221,3);
+constraint set_eq(X_INTRODUCED_222,1..0);
+constraint set_eq(X_INTRODUCED_223,1..0);
+constraint set_eq(X_INTRODUCED_224,1..0);
+constraint int_eq(X_INTRODUCED_225,3);
+constraint set_eq(X_INTRODUCED_226,1..0);
+constraint set_eq(X_INTRODUCED_227,1..0);
+constraint int_eq(X_INTRODUCED_228,3);
+constraint set_eq(X_INTRODUCED_229,1..0);
+constraint int_eq(X_INTRODUCED_230,3);
+constraint int_eq(X_INTRODUCED_231,3);
+constraint set_eq(X_INTRODUCED_232,1..0);
+constraint set_eq(X_INTRODUCED_233,1..0);
+constraint set_eq(X_INTRODUCED_234,1..0);
+constraint int_eq(X_INTRODUCED_235,3);
+constraint set_eq(X_INTRODUCED_236,1..0);
+constraint set_eq(X_INTRODUCED_237,1..0);
+constraint int_eq(X_INTRODUCED_238,3);
+constraint set_eq(X_INTRODUCED_239,1..0);
+constraint int_eq(X_INTRODUCED_240,3);
+constraint int_eq(X_INTRODUCED_241,3);
+constraint set_eq(X_INTRODUCED_242,1..0);
+constraint set_eq(X_INTRODUCED_243,1..0);
+constraint set_eq(X_INTRODUCED_244,1..0);
+constraint int_eq(X_INTRODUCED_245,3);
+constraint set_eq(X_INTRODUCED_246,1..0);
+constraint set_eq(X_INTRODUCED_247,1..0);
+constraint int_eq(X_INTRODUCED_248,3);
+constraint set_eq(X_INTRODUCED_249,1..0);
+constraint int_eq(X_INTRODUCED_250,3);
+constraint int_eq(X_INTRODUCED_251,3);
+constraint set_lt(X_INTRODUCED_0,X_INTRODUCED_4);
+%constraint set_lt(X_INTRODUCED_4,X_INTRODUCED_8);
+%constraint set_lt(X_INTRODUCED_8,X_INTRODUCED_12);
+constraint set_in(1,X_INTRODUCED_4);
+constraint set_in(2,X_INTRODUCED_5);
+constraint set_in(3,X_INTRODUCED_6);
+constraint set_in(1,X_INTRODUCED_8);
+constraint set_in(2,X_INTRODUCED_9);
+constraint set_in(3,X_INTRODUCED_10);
+constraint set_in(1,X_INTRODUCED_12);
+constraint set_in(2,X_INTRODUCED_13);
+constraint set_in(3,X_INTRODUCED_14);
+constraint set_in(4,X_INTRODUCED_4);
+constraint set_in(7,X_INTRODUCED_4);
+constraint set_in(1,X_INTRODUCED_0);
+constraint set_in(2,X_INTRODUCED_0);
+constraint set_in(3,X_INTRODUCED_0);
+constraint set_in(4,X_INTRODUCED_1);
+constraint set_in(5,X_INTRODUCED_1);
+constraint set_in(6,X_INTRODUCED_1);
+constraint set_in(7,X_INTRODUCED_2);
+constraint set_in(8,X_INTRODUCED_2);
+constraint set_in(9,X_INTRODUCED_2);
+constraint set_in(10,X_INTRODUCED_3);
+constraint set_in(11,X_INTRODUCED_3);
+constraint set_in(12,X_INTRODUCED_3);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_4,X_INTRODUCED_16):: defines_var(X_INTRODUCED_16);
+constraint set_card(X_INTRODUCED_16,X_INTRODUCED_17):: defines_var(X_INTRODUCED_17);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_5,X_INTRODUCED_18):: defines_var(X_INTRODUCED_18);
+constraint set_card(X_INTRODUCED_18,X_INTRODUCED_19):: defines_var(X_INTRODUCED_19);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_6,X_INTRODUCED_20):: defines_var(X_INTRODUCED_20);
+constraint set_card(X_INTRODUCED_20,X_INTRODUCED_21):: defines_var(X_INTRODUCED_21);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_7,X_INTRODUCED_22):: defines_var(X_INTRODUCED_22);
+constraint set_card(X_INTRODUCED_22,X_INTRODUCED_23):: defines_var(X_INTRODUCED_23);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_4,X_INTRODUCED_24):: defines_var(X_INTRODUCED_24);
+constraint set_card(X_INTRODUCED_24,X_INTRODUCED_25):: defines_var(X_INTRODUCED_25);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_5,X_INTRODUCED_26):: defines_var(X_INTRODUCED_26);
+constraint set_card(X_INTRODUCED_26,X_INTRODUCED_27):: defines_var(X_INTRODUCED_27);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_6,X_INTRODUCED_28):: defines_var(X_INTRODUCED_28);
+constraint set_card(X_INTRODUCED_28,X_INTRODUCED_29):: defines_var(X_INTRODUCED_29);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_7,X_INTRODUCED_30):: defines_var(X_INTRODUCED_30);
+constraint set_card(X_INTRODUCED_30,X_INTRODUCED_31):: defines_var(X_INTRODUCED_31);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_4,X_INTRODUCED_32):: defines_var(X_INTRODUCED_32);
+constraint set_card(X_INTRODUCED_32,X_INTRODUCED_33):: defines_var(X_INTRODUCED_33);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_5,X_INTRODUCED_34):: defines_var(X_INTRODUCED_34);
+constraint set_card(X_INTRODUCED_34,X_INTRODUCED_35):: defines_var(X_INTRODUCED_35);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_6,X_INTRODUCED_36):: defines_var(X_INTRODUCED_36);
+constraint set_card(X_INTRODUCED_36,X_INTRODUCED_37):: defines_var(X_INTRODUCED_37);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_7,X_INTRODUCED_38):: defines_var(X_INTRODUCED_38);
+constraint set_card(X_INTRODUCED_38,X_INTRODUCED_39):: defines_var(X_INTRODUCED_39);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_4,X_INTRODUCED_40):: defines_var(X_INTRODUCED_40);
+constraint set_card(X_INTRODUCED_40,X_INTRODUCED_41):: defines_var(X_INTRODUCED_41);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_5,X_INTRODUCED_42):: defines_var(X_INTRODUCED_42);
+constraint set_card(X_INTRODUCED_42,X_INTRODUCED_43):: defines_var(X_INTRODUCED_43);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_6,X_INTRODUCED_44):: defines_var(X_INTRODUCED_44);
+constraint set_card(X_INTRODUCED_44,X_INTRODUCED_45):: defines_var(X_INTRODUCED_45);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_7,X_INTRODUCED_46):: defines_var(X_INTRODUCED_46);
+constraint set_card(X_INTRODUCED_46,X_INTRODUCED_47):: defines_var(X_INTRODUCED_47);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_8,X_INTRODUCED_48):: defines_var(X_INTRODUCED_48);
+constraint set_card(X_INTRODUCED_48,X_INTRODUCED_49):: defines_var(X_INTRODUCED_49);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_9,X_INTRODUCED_50):: defines_var(X_INTRODUCED_50);
+constraint set_card(X_INTRODUCED_50,X_INTRODUCED_51):: defines_var(X_INTRODUCED_51);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_10,X_INTRODUCED_52):: defines_var(X_INTRODUCED_52);
+constraint set_card(X_INTRODUCED_52,X_INTRODUCED_53):: defines_var(X_INTRODUCED_53);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_11,X_INTRODUCED_54):: defines_var(X_INTRODUCED_54);
+constraint set_card(X_INTRODUCED_54,X_INTRODUCED_55):: defines_var(X_INTRODUCED_55);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_8,X_INTRODUCED_56):: defines_var(X_INTRODUCED_56);
+constraint set_card(X_INTRODUCED_56,X_INTRODUCED_57):: defines_var(X_INTRODUCED_57);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_9,X_INTRODUCED_58):: defines_var(X_INTRODUCED_58);
+constraint set_card(X_INTRODUCED_58,X_INTRODUCED_59):: defines_var(X_INTRODUCED_59);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_10,X_INTRODUCED_60):: defines_var(X_INTRODUCED_60);
+constraint set_card(X_INTRODUCED_60,X_INTRODUCED_61):: defines_var(X_INTRODUCED_61);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_11,X_INTRODUCED_62):: defines_var(X_INTRODUCED_62);
+constraint set_card(X_INTRODUCED_62,X_INTRODUCED_63):: defines_var(X_INTRODUCED_63);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_8,X_INTRODUCED_64):: defines_var(X_INTRODUCED_64);
+constraint set_card(X_INTRODUCED_64,X_INTRODUCED_65):: defines_var(X_INTRODUCED_65);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_9,X_INTRODUCED_66):: defines_var(X_INTRODUCED_66);
+constraint set_card(X_INTRODUCED_66,X_INTRODUCED_67):: defines_var(X_INTRODUCED_67);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_10,X_INTRODUCED_68):: defines_var(X_INTRODUCED_68);
+constraint set_card(X_INTRODUCED_68,X_INTRODUCED_69):: defines_var(X_INTRODUCED_69);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_11,X_INTRODUCED_70):: defines_var(X_INTRODUCED_70);
+constraint set_card(X_INTRODUCED_70,X_INTRODUCED_71):: defines_var(X_INTRODUCED_71);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_8,X_INTRODUCED_72):: defines_var(X_INTRODUCED_72);
+constraint set_card(X_INTRODUCED_72,X_INTRODUCED_73):: defines_var(X_INTRODUCED_73);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_9,X_INTRODUCED_74):: defines_var(X_INTRODUCED_74);
+constraint set_card(X_INTRODUCED_74,X_INTRODUCED_75):: defines_var(X_INTRODUCED_75);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_10,X_INTRODUCED_76):: defines_var(X_INTRODUCED_76);
+constraint set_card(X_INTRODUCED_76,X_INTRODUCED_77):: defines_var(X_INTRODUCED_77);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_11,X_INTRODUCED_78):: defines_var(X_INTRODUCED_78);
+constraint set_card(X_INTRODUCED_78,X_INTRODUCED_79):: defines_var(X_INTRODUCED_79);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_12,X_INTRODUCED_80):: defines_var(X_INTRODUCED_80);
+constraint set_card(X_INTRODUCED_80,X_INTRODUCED_81):: defines_var(X_INTRODUCED_81);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_13,X_INTRODUCED_82):: defines_var(X_INTRODUCED_82);
+constraint set_card(X_INTRODUCED_82,X_INTRODUCED_83):: defines_var(X_INTRODUCED_83);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_14,X_INTRODUCED_84):: defines_var(X_INTRODUCED_84);
+constraint set_card(X_INTRODUCED_84,X_INTRODUCED_85):: defines_var(X_INTRODUCED_85);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_15,X_INTRODUCED_86):: defines_var(X_INTRODUCED_86);
+constraint set_card(X_INTRODUCED_86,X_INTRODUCED_87):: defines_var(X_INTRODUCED_87);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_12,X_INTRODUCED_88):: defines_var(X_INTRODUCED_88);
+constraint set_card(X_INTRODUCED_88,X_INTRODUCED_89):: defines_var(X_INTRODUCED_89);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_13,X_INTRODUCED_90):: defines_var(X_INTRODUCED_90);
+constraint set_card(X_INTRODUCED_90,X_INTRODUCED_91):: defines_var(X_INTRODUCED_91);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_14,X_INTRODUCED_92):: defines_var(X_INTRODUCED_92);
+constraint set_card(X_INTRODUCED_92,X_INTRODUCED_93):: defines_var(X_INTRODUCED_93);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_15,X_INTRODUCED_94):: defines_var(X_INTRODUCED_94);
+constraint set_card(X_INTRODUCED_94,X_INTRODUCED_95):: defines_var(X_INTRODUCED_95);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_12,X_INTRODUCED_96):: defines_var(X_INTRODUCED_96);
+constraint set_card(X_INTRODUCED_96,X_INTRODUCED_97):: defines_var(X_INTRODUCED_97);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_13,X_INTRODUCED_98):: defines_var(X_INTRODUCED_98);
+constraint set_card(X_INTRODUCED_98,X_INTRODUCED_99):: defines_var(X_INTRODUCED_99);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_14,X_INTRODUCED_100):: defines_var(X_INTRODUCED_100);
+constraint set_card(X_INTRODUCED_100,X_INTRODUCED_101):: defines_var(X_INTRODUCED_101);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_15,X_INTRODUCED_102):: defines_var(X_INTRODUCED_102);
+constraint set_card(X_INTRODUCED_102,X_INTRODUCED_103):: defines_var(X_INTRODUCED_103);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_12,X_INTRODUCED_104):: defines_var(X_INTRODUCED_104);
+constraint set_card(X_INTRODUCED_104,X_INTRODUCED_105):: defines_var(X_INTRODUCED_105);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_13,X_INTRODUCED_106):: defines_var(X_INTRODUCED_106);
+constraint set_card(X_INTRODUCED_106,X_INTRODUCED_107):: defines_var(X_INTRODUCED_107);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_14,X_INTRODUCED_108):: defines_var(X_INTRODUCED_108);
+constraint set_card(X_INTRODUCED_108,X_INTRODUCED_109):: defines_var(X_INTRODUCED_109);
+constraint set_intersect(X_INTRODUCED_3,X_INTRODUCED_15,X_INTRODUCED_110):: defines_var(X_INTRODUCED_110);
+constraint set_card(X_INTRODUCED_110,X_INTRODUCED_111):: defines_var(X_INTRODUCED_111);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_8,X_INTRODUCED_112):: defines_var(X_INTRODUCED_112);
+constraint set_card(X_INTRODUCED_112,X_INTRODUCED_113):: defines_var(X_INTRODUCED_113);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_9,X_INTRODUCED_114):: defines_var(X_INTRODUCED_114);
+constraint set_card(X_INTRODUCED_114,X_INTRODUCED_115):: defines_var(X_INTRODUCED_115);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_10,X_INTRODUCED_116):: defines_var(X_INTRODUCED_116);
+constraint set_card(X_INTRODUCED_116,X_INTRODUCED_117):: defines_var(X_INTRODUCED_117);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_11,X_INTRODUCED_118):: defines_var(X_INTRODUCED_118);
+constraint set_card(X_INTRODUCED_118,X_INTRODUCED_119):: defines_var(X_INTRODUCED_119);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_8,X_INTRODUCED_120):: defines_var(X_INTRODUCED_120);
+constraint set_card(X_INTRODUCED_120,X_INTRODUCED_121):: defines_var(X_INTRODUCED_121);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_9,X_INTRODUCED_122):: defines_var(X_INTRODUCED_122);
+constraint set_card(X_INTRODUCED_122,X_INTRODUCED_123):: defines_var(X_INTRODUCED_123);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_10,X_INTRODUCED_124):: defines_var(X_INTRODUCED_124);
+constraint set_card(X_INTRODUCED_124,X_INTRODUCED_125):: defines_var(X_INTRODUCED_125);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_11,X_INTRODUCED_126):: defines_var(X_INTRODUCED_126);
+constraint set_card(X_INTRODUCED_126,X_INTRODUCED_127):: defines_var(X_INTRODUCED_127);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_8,X_INTRODUCED_128):: defines_var(X_INTRODUCED_128);
+constraint set_card(X_INTRODUCED_128,X_INTRODUCED_129):: defines_var(X_INTRODUCED_129);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_9,X_INTRODUCED_130):: defines_var(X_INTRODUCED_130);
+constraint set_card(X_INTRODUCED_130,X_INTRODUCED_131):: defines_var(X_INTRODUCED_131);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_10,X_INTRODUCED_132):: defines_var(X_INTRODUCED_132);
+constraint set_card(X_INTRODUCED_132,X_INTRODUCED_133):: defines_var(X_INTRODUCED_133);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_11,X_INTRODUCED_134):: defines_var(X_INTRODUCED_134);
+constraint set_card(X_INTRODUCED_134,X_INTRODUCED_135):: defines_var(X_INTRODUCED_135);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_8,X_INTRODUCED_136):: defines_var(X_INTRODUCED_136);
+constraint set_card(X_INTRODUCED_136,X_INTRODUCED_137):: defines_var(X_INTRODUCED_137);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_9,X_INTRODUCED_138):: defines_var(X_INTRODUCED_138);
+constraint set_card(X_INTRODUCED_138,X_INTRODUCED_139):: defines_var(X_INTRODUCED_139);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_10,X_INTRODUCED_140):: defines_var(X_INTRODUCED_140);
+constraint set_card(X_INTRODUCED_140,X_INTRODUCED_141):: defines_var(X_INTRODUCED_141);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_11,X_INTRODUCED_142):: defines_var(X_INTRODUCED_142);
+constraint set_card(X_INTRODUCED_142,X_INTRODUCED_143):: defines_var(X_INTRODUCED_143);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_12,X_INTRODUCED_144):: defines_var(X_INTRODUCED_144);
+constraint set_card(X_INTRODUCED_144,X_INTRODUCED_145):: defines_var(X_INTRODUCED_145);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_13,X_INTRODUCED_146):: defines_var(X_INTRODUCED_146);
+constraint set_card(X_INTRODUCED_146,X_INTRODUCED_147):: defines_var(X_INTRODUCED_147);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_14,X_INTRODUCED_148):: defines_var(X_INTRODUCED_148);
+constraint set_card(X_INTRODUCED_148,X_INTRODUCED_149):: defines_var(X_INTRODUCED_149);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_15,X_INTRODUCED_150):: defines_var(X_INTRODUCED_150);
+constraint set_card(X_INTRODUCED_150,X_INTRODUCED_151):: defines_var(X_INTRODUCED_151);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_12,X_INTRODUCED_152):: defines_var(X_INTRODUCED_152);
+constraint set_card(X_INTRODUCED_152,X_INTRODUCED_153):: defines_var(X_INTRODUCED_153);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_13,X_INTRODUCED_154):: defines_var(X_INTRODUCED_154);
+constraint set_card(X_INTRODUCED_154,X_INTRODUCED_155):: defines_var(X_INTRODUCED_155);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_14,X_INTRODUCED_156):: defines_var(X_INTRODUCED_156);
+constraint set_card(X_INTRODUCED_156,X_INTRODUCED_157):: defines_var(X_INTRODUCED_157);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_15,X_INTRODUCED_158):: defines_var(X_INTRODUCED_158);
+constraint set_card(X_INTRODUCED_158,X_INTRODUCED_159):: defines_var(X_INTRODUCED_159);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_12,X_INTRODUCED_160):: defines_var(X_INTRODUCED_160);
+constraint set_card(X_INTRODUCED_160,X_INTRODUCED_161):: defines_var(X_INTRODUCED_161);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_13,X_INTRODUCED_162):: defines_var(X_INTRODUCED_162);
+constraint set_card(X_INTRODUCED_162,X_INTRODUCED_163):: defines_var(X_INTRODUCED_163);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_14,X_INTRODUCED_164):: defines_var(X_INTRODUCED_164);
+constraint set_card(X_INTRODUCED_164,X_INTRODUCED_165):: defines_var(X_INTRODUCED_165);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_15,X_INTRODUCED_166):: defines_var(X_INTRODUCED_166);
+constraint set_card(X_INTRODUCED_166,X_INTRODUCED_167):: defines_var(X_INTRODUCED_167);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_12,X_INTRODUCED_168):: defines_var(X_INTRODUCED_168);
+constraint set_card(X_INTRODUCED_168,X_INTRODUCED_169):: defines_var(X_INTRODUCED_169);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_13,X_INTRODUCED_170):: defines_var(X_INTRODUCED_170);
+constraint set_card(X_INTRODUCED_170,X_INTRODUCED_171):: defines_var(X_INTRODUCED_171);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_14,X_INTRODUCED_172):: defines_var(X_INTRODUCED_172);
+constraint set_card(X_INTRODUCED_172,X_INTRODUCED_173):: defines_var(X_INTRODUCED_173);
+constraint set_intersect(X_INTRODUCED_7,X_INTRODUCED_15,X_INTRODUCED_174):: defines_var(X_INTRODUCED_174);
+constraint set_card(X_INTRODUCED_174,X_INTRODUCED_175):: defines_var(X_INTRODUCED_175);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_12,X_INTRODUCED_176):: defines_var(X_INTRODUCED_176);
+constraint set_card(X_INTRODUCED_176,X_INTRODUCED_177):: defines_var(X_INTRODUCED_177);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_13,X_INTRODUCED_178):: defines_var(X_INTRODUCED_178);
+constraint set_card(X_INTRODUCED_178,X_INTRODUCED_179):: defines_var(X_INTRODUCED_179);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_14,X_INTRODUCED_180):: defines_var(X_INTRODUCED_180);
+constraint set_card(X_INTRODUCED_180,X_INTRODUCED_181):: defines_var(X_INTRODUCED_181);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_15,X_INTRODUCED_182):: defines_var(X_INTRODUCED_182);
+constraint set_card(X_INTRODUCED_182,X_INTRODUCED_183):: defines_var(X_INTRODUCED_183);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_12,X_INTRODUCED_184):: defines_var(X_INTRODUCED_184);
+constraint set_card(X_INTRODUCED_184,X_INTRODUCED_185):: defines_var(X_INTRODUCED_185);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_13,X_INTRODUCED_186):: defines_var(X_INTRODUCED_186);
+constraint set_card(X_INTRODUCED_186,X_INTRODUCED_187):: defines_var(X_INTRODUCED_187);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_14,X_INTRODUCED_188):: defines_var(X_INTRODUCED_188);
+constraint set_card(X_INTRODUCED_188,X_INTRODUCED_189):: defines_var(X_INTRODUCED_189);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_15,X_INTRODUCED_190):: defines_var(X_INTRODUCED_190);
+constraint set_card(X_INTRODUCED_190,X_INTRODUCED_191):: defines_var(X_INTRODUCED_191);
+constraint set_intersect(X_INTRODUCED_10,X_INTRODUCED_12,X_INTRODUCED_192):: defines_var(X_INTRODUCED_192);
+constraint set_card(X_INTRODUCED_192,X_INTRODUCED_193):: defines_var(X_INTRODUCED_193);
+constraint set_intersect(X_INTRODUCED_10,X_INTRODUCED_13,X_INTRODUCED_194):: defines_var(X_INTRODUCED_194);
+constraint set_card(X_INTRODUCED_194,X_INTRODUCED_195):: defines_var(X_INTRODUCED_195);
+constraint set_intersect(X_INTRODUCED_10,X_INTRODUCED_14,X_INTRODUCED_196):: defines_var(X_INTRODUCED_196);
+constraint set_card(X_INTRODUCED_196,X_INTRODUCED_197):: defines_var(X_INTRODUCED_197);
+constraint set_intersect(X_INTRODUCED_10,X_INTRODUCED_15,X_INTRODUCED_198):: defines_var(X_INTRODUCED_198);
+constraint set_card(X_INTRODUCED_198,X_INTRODUCED_199):: defines_var(X_INTRODUCED_199);
+constraint set_intersect(X_INTRODUCED_11,X_INTRODUCED_12,X_INTRODUCED_200):: defines_var(X_INTRODUCED_200);
+constraint set_card(X_INTRODUCED_200,X_INTRODUCED_201):: defines_var(X_INTRODUCED_201);
+constraint set_intersect(X_INTRODUCED_11,X_INTRODUCED_13,X_INTRODUCED_202):: defines_var(X_INTRODUCED_202);
+constraint set_card(X_INTRODUCED_202,X_INTRODUCED_203):: defines_var(X_INTRODUCED_203);
+constraint set_intersect(X_INTRODUCED_11,X_INTRODUCED_14,X_INTRODUCED_204):: defines_var(X_INTRODUCED_204);
+constraint set_card(X_INTRODUCED_204,X_INTRODUCED_205):: defines_var(X_INTRODUCED_205);
+constraint set_intersect(X_INTRODUCED_11,X_INTRODUCED_15,X_INTRODUCED_206):: defines_var(X_INTRODUCED_206);
+constraint set_card(X_INTRODUCED_206,X_INTRODUCED_207):: defines_var(X_INTRODUCED_207);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_1,X_INTRODUCED_212):: defines_var(X_INTRODUCED_212);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_2,X_INTRODUCED_213):: defines_var(X_INTRODUCED_213);
+constraint set_intersect(X_INTRODUCED_0,X_INTRODUCED_3,X_INTRODUCED_214):: defines_var(X_INTRODUCED_214);
+constraint set_card(X_INTRODUCED_0,X_INTRODUCED_215):: defines_var(X_INTRODUCED_215);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_2,X_INTRODUCED_216):: defines_var(X_INTRODUCED_216);
+constraint set_intersect(X_INTRODUCED_1,X_INTRODUCED_3,X_INTRODUCED_217):: defines_var(X_INTRODUCED_217);
+constraint set_card(X_INTRODUCED_1,X_INTRODUCED_218):: defines_var(X_INTRODUCED_218);
+constraint set_intersect(X_INTRODUCED_2,X_INTRODUCED_3,X_INTRODUCED_219):: defines_var(X_INTRODUCED_219);
+constraint set_card(X_INTRODUCED_2,X_INTRODUCED_220):: defines_var(X_INTRODUCED_220);
+constraint set_card(X_INTRODUCED_3,X_INTRODUCED_221):: defines_var(X_INTRODUCED_221);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_5,X_INTRODUCED_222):: defines_var(X_INTRODUCED_222);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_6,X_INTRODUCED_223):: defines_var(X_INTRODUCED_223);
+constraint set_intersect(X_INTRODUCED_4,X_INTRODUCED_7,X_INTRODUCED_224):: defines_var(X_INTRODUCED_224);
+constraint set_card(X_INTRODUCED_4,X_INTRODUCED_225):: defines_var(X_INTRODUCED_225);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_6,X_INTRODUCED_226):: defines_var(X_INTRODUCED_226);
+constraint set_intersect(X_INTRODUCED_5,X_INTRODUCED_7,X_INTRODUCED_227):: defines_var(X_INTRODUCED_227);
+constraint set_card(X_INTRODUCED_5,X_INTRODUCED_228):: defines_var(X_INTRODUCED_228);
+constraint set_intersect(X_INTRODUCED_6,X_INTRODUCED_7,X_INTRODUCED_229):: defines_var(X_INTRODUCED_229);
+constraint set_card(X_INTRODUCED_6,X_INTRODUCED_230):: defines_var(X_INTRODUCED_230);
+constraint set_card(X_INTRODUCED_7,X_INTRODUCED_231):: defines_var(X_INTRODUCED_231);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_9,X_INTRODUCED_232):: defines_var(X_INTRODUCED_232);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_10,X_INTRODUCED_233):: defines_var(X_INTRODUCED_233);
+constraint set_intersect(X_INTRODUCED_8,X_INTRODUCED_11,X_INTRODUCED_234):: defines_var(X_INTRODUCED_234);
+constraint set_card(X_INTRODUCED_8,X_INTRODUCED_235):: defines_var(X_INTRODUCED_235);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_10,X_INTRODUCED_236):: defines_var(X_INTRODUCED_236);
+constraint set_intersect(X_INTRODUCED_9,X_INTRODUCED_11,X_INTRODUCED_237):: defines_var(X_INTRODUCED_237);
+constraint set_card(X_INTRODUCED_9,X_INTRODUCED_238):: defines_var(X_INTRODUCED_238);
+constraint set_intersect(X_INTRODUCED_10,X_INTRODUCED_11,X_INTRODUCED_239):: defines_var(X_INTRODUCED_239);
+constraint set_card(X_INTRODUCED_10,X_INTRODUCED_240):: defines_var(X_INTRODUCED_240);
+constraint set_card(X_INTRODUCED_11,X_INTRODUCED_241):: defines_var(X_INTRODUCED_241);
+constraint set_intersect(X_INTRODUCED_12,X_INTRODUCED_13,X_INTRODUCED_242):: defines_var(X_INTRODUCED_242);
+constraint set_intersect(X_INTRODUCED_12,X_INTRODUCED_14,X_INTRODUCED_243):: defines_var(X_INTRODUCED_243);
+constraint set_intersect(X_INTRODUCED_12,X_INTRODUCED_15,X_INTRODUCED_244):: defines_var(X_INTRODUCED_244);
+constraint set_card(X_INTRODUCED_12,X_INTRODUCED_245):: defines_var(X_INTRODUCED_245);
+constraint set_intersect(X_INTRODUCED_13,X_INTRODUCED_14,X_INTRODUCED_246):: defines_var(X_INTRODUCED_246);
+constraint set_intersect(X_INTRODUCED_13,X_INTRODUCED_15,X_INTRODUCED_247):: defines_var(X_INTRODUCED_247);
+constraint set_card(X_INTRODUCED_13,X_INTRODUCED_248):: defines_var(X_INTRODUCED_248);
+constraint set_intersect(X_INTRODUCED_14,X_INTRODUCED_15,X_INTRODUCED_249):: defines_var(X_INTRODUCED_249);
+constraint set_card(X_INTRODUCED_14,X_INTRODUCED_250):: defines_var(X_INTRODUCED_250);
+constraint set_card(X_INTRODUCED_15,X_INTRODUCED_251):: defines_var(X_INTRODUCED_251);
+solve satisfy;
diff --git a/software/minizinc/docs/chi/examples/social-golfers.mzn b/software/minizinc/docs/chi/examples/social-golfers.mzn
new file mode 100644
index 0000000..16473ec
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/social-golfers.mzn
@@ -0,0 +1,53 @@
+include "partition_set.mzn";
+int: weeks; set of int: WEEK = 1..weeks;
+int: groups; set of int: GROUP = 1..groups;
+int: size; set of int: SIZE = 1..size;
+int: ngolfers = groups*size;
+set of int: GOLFER = 1..ngolfers;
+
+array[WEEK,GROUP] of var set of GOLFER: Sched;
+
+% constraints
+constraint
+ forall (i in 1..weeks-1) (
+ Sched[i,1] < Sched[i+1,1]
+ ) /\
+ forall (i in WEEK, j in GROUP) (
+ card(Sched[i,j]) = size
+ /\ forall (k in j+1..groups) (
+% Sched[i,j] < Sched[i,k]
+% /\
+ Sched[i,j] intersect Sched[i,k] = {}
+ )
+ ) /\
+ forall (i in WEEK) (
+ partition_set([Sched[i,j] | j in GROUP], GOLFER)
+% /\ forall (j in 1..groups-1) (
+% Sched[i,j] < Sched[i,j+1]
+% )
+ ) /\
+ forall (i in 1..weeks-1, j in i+1..weeks) (
+ forall (x,y in GROUP) (
+ card(Sched[i,x] intersect Sched[j,y]) <= 1
+ )
+ );
+% symmetry
+ constraint
+ % Fix the first week %
+ forall (i in GROUP, j in SIZE) (
+ ((i-1)*size + j) in Sched[1,i]
+ ) /\
+ % Fix first group of second week %
+ forall (i in SIZE) (
+ ((i-1)*size + 1) in Sched[2,1]
+ ) /\
+ % Fix first 'size' players
+ forall (w in 2..weeks, p in SIZE) (
+ p in Sched[w,p]
+ );
+
+solve satisfy;
+
+output [ show(Sched[i,j]) ++ " " ++
+ if j == groups then "\n" else "" endif |
+ i in WEEK, j in GROUP ];
diff --git a/software/minizinc/docs/chi/examples/social-golfers.ozn b/software/minizinc/docs/chi/examples/social-golfers.ozn
new file mode 100644
index 0000000..e106fb6
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/social-golfers.ozn
@@ -0,0 +1,5 @@
+output [(show(Sched[i,j])++" ")++if j==groups then "\n" else "" endif | i in WEEK, j in GROUP, ];
+set of int: WEEK = 1..4;
+int: groups = 4;
+set of int: GROUP = 1..4;
+array [WEEK,GROUP] of set of int: Sched;
diff --git a/software/minizinc/docs/chi/examples/sonet.dzn b/software/minizinc/docs/chi/examples/sonet.dzn
new file mode 100644
index 0000000..0cd0406
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/sonet.dzn
@@ -0,0 +1,4 @@
+nb_nodes = 5;
+nb_rings = 2;
+capacity = 4;
+Demand = { (1,3), (3,5), (3,2), (2,4), (4,1) };
diff --git a/software/minizinc/docs/chi/examples/stable-marriage.dzn b/software/minizinc/docs/chi/examples/stable-marriage.dzn
new file mode 100644
index 0000000..7370207
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/stable-marriage.dzn
@@ -0,0 +1,14 @@
+n = 5;
+rankWomen =
+ [| 1, 2, 4, 3, 5,
+ | 3, 5, 1, 2, 4,
+ | 5, 4, 2, 1, 3,
+ | 1, 3, 5, 4, 2,
+ | 4, 2, 3, 5, 1 |];
+
+rankMen =
+ [| 5, 1, 2, 4, 3,
+ | 4, 1, 3, 2, 5,
+ | 5, 3, 2, 4, 1,
+ | 1, 5, 4, 3, 2,
+ | 4, 3, 2, 1, 5 |];
diff --git a/software/minizinc/docs/chi/examples/stable-marriage.mzn b/software/minizinc/docs/chi/examples/stable-marriage.mzn
new file mode 100644
index 0000000..08f179e
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/stable-marriage.mzn
@@ -0,0 +1,25 @@
+int: n;
+
+enum Men = anon_enum(n);
+enum Women = anon_enum(n);
+
+array[Women, Men] of int: rankWomen;
+array[Men, Women] of int: rankMen;
+
+array[Men] of var Women: wife;
+array[Women] of var Men: husband;
+
+% assignment
+constraint forall (m in Men) (husband[wife[m]]=m);
+constraint forall (w in Women) (wife[husband[w]]=w);
+% ranking
+constraint forall (m in Men, o in Women) (
+ rankMen[m,o] < rankMen[m,wife[m]] ->
+ rankWomen[o,husband[o]] < rankWomen[o,m] );
+
+constraint forall (w in Women, o in Men) (
+ rankWomen[w,o] < rankWomen[w,husband[w]] ->
+ rankMen[o,wife[o]] < rankMen[o,w] );
+solve satisfy;
+
+output ["wives= \(wife)\nhusbands= \(husband)\n"];
diff --git a/software/minizinc/docs/chi/examples/sudoku.dzn b/software/minizinc/docs/chi/examples/sudoku.dzn
new file mode 100644
index 0000000..4b3d5df
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/sudoku.dzn
@@ -0,0 +1,11 @@
+S=3;
+start=[|
+0, 0, 0, 0, 0, 0, 0, 0, 0|
+0, 6, 8, 4, 0, 1, 0, 7, 0|
+0, 0, 0, 0, 8, 5, 0, 3, 0|
+0, 2, 6, 8, 0, 9, 0, 4, 0|
+0, 0, 7, 0, 0, 0, 9, 0, 0|
+0, 5, 0, 1, 0, 6, 3, 2, 0|
+0, 4, 0, 6, 1, 0, 0, 0, 0|
+0, 3, 0, 2, 0, 7, 6, 9, 0|
+0, 0, 0, 0, 0, 0, 0, 0, 0|];
diff --git a/software/minizinc/docs/chi/examples/sudoku.mzn b/software/minizinc/docs/chi/examples/sudoku.mzn
new file mode 100644
index 0000000..494a603
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/sudoku.mzn
@@ -0,0 +1,39 @@
+include "alldifferent.mzn";
+
+int: S;
+int: N = S * S;
+int: digs = ceil(log(10.0,int2float(N))); % 输出的数字
+
+set of int: PuzzleRange = 1..N;
+set of int: SubSquareRange = 1..S;
+
+array[1..N,1..N] of 0..N: start; %% 板初始0 = 空
+array[1..N,1..N] of var PuzzleRange: puzzle;
+
+% 填充初始板
+constraint forall(i,j in PuzzleRange)(
+ if start[i,j] > 0 then puzzle[i,j] = start[i,j] else true endif );
+
+% 每行中取值各不相同
+constraint forall (i in PuzzleRange) (
+ alldifferent( [ puzzle[i,j] | j in PuzzleRange ]) );
+
+% 每列中取值各不相同
+constraint forall (j in PuzzleRange) (
+ alldifferent( [ puzzle[i,j] | i in PuzzleRange ]) );
+
+% 每个子方格块中取值各不相同
+constraint
+ forall (a, o in SubSquareRange)(
+ alldifferent( [ puzzle[(a-1) *S + a1, (o-1)*S + o1] |
+ a1, o1 in SubSquareRange ] ) );
+
+solve satisfy;
+
+output [ show_int(digs,puzzle[i,j]) ++ " " ++
+ if j mod S == 0 then " " else "" endif ++
+ if j == N then
+ if i != N then
+ if i mod S == 0 then "\n\n" else "\n" endif
+ else "" endif else "" endif
+ | i,j in PuzzleRange ] ++ ["\n"];
diff --git a/software/minizinc/docs/chi/examples/uboolsum.mzn b/software/minizinc/docs/chi/examples/uboolsum.mzn
new file mode 100644
index 0000000..b9c5afb
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/uboolsum.mzn
@@ -0,0 +1,17 @@
+% 布尔型变量 x的总和 = s
+predicate bool_sum_eq(array[int] of var bool:x, int:s) =
+ let { int: c = length(x) } in
+ if s < 0 then false
+ elseif s == 0 then forall(i in 1..c)(x[i] == false)
+ elseif s < c then
+ let { % cp = nearest power of 2 >= c
+ int: cp = pow(2,ceil(log2(int2float(c)))),
+ array[1..cp] of var bool:y, % y is padded version of x
+ array[1..cp] of var bool:z } in
+ forall(i in 1..c)(y[i] == x[i]) /\
+ forall(i in c+1..cp)(y[i] == false) /\
+ oesort(y, z) /\ z[s] == true /\ z[s+1] == false
+ elseif s == c then forall(i in 1..c)(x[i] == true)
+ else false endif;
+
+include "oesort.mzn";
diff --git a/software/minizinc/docs/chi/examples/unbounded.mzn b/software/minizinc/docs/chi/examples/unbounded.mzn
new file mode 100644
index 0000000..f1c354a
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/unbounded.mzn
@@ -0,0 +1,10 @@
+var int: a;
+var int: b;
+
+constraint 200*a + 150 * b <= 4000;
+constraint 100*a + 250 * b >= 0;
+
+solve satisfy;
+
+output ["a = ",show(a), " b = ", show(b), "\n"];
+%output ["a = \(a);\n"];
diff --git a/software/minizinc/docs/chi/examples/unconstrained.mzn b/software/minizinc/docs/chi/examples/unconstrained.mzn
new file mode 100644
index 0000000..d6d9ac6
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/unconstrained.mzn
@@ -0,0 +1,10 @@
+include "alldifferent.mzn";
+
+array[1..15] of var bool: b;
+array[1..4] of var 1..10: x;
+
+constraint alldifferent(x) /\ sum(i in 1..4)(x[i]) = 9;
+
+solve satisfy;
+
+output ["b = \(b);\nx = \(x);\n"]
diff --git a/software/minizinc/docs/chi/examples/wedding.mzn b/software/minizinc/docs/chi/examples/wedding.mzn
new file mode 100644
index 0000000..3e790a4
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/wedding.mzn
@@ -0,0 +1,33 @@
+enum Guests = { bride, groom, bestman, bridesmaid, bob, carol,
+ ted, alice, ron, rona, ed, clara};
+set of int: Seats = 1..12;
+set of int: Hatreds = 1..5;
+array[Hatreds] of Guests: h1 = [groom, carol, ed, bride, ted];
+array[Hatreds] of Guests: h2 = [clara, bestman, ted, alice, ron];
+set of Guests: Males = {groom, bestman, bob, ted, ron,ed};
+set of Guests: Females = {bride,bridesmaid,carol,alice,rona,clara};
+
+array[Guests] of var Seats: pos; % 客人的座位
+array[Hatreds] of var Seats: p1; % 互相憎恶的客人1的座位
+array[Hatreds] of var Seats: p2; % 互相憎恶的客人2的座位
+array[Hatreds] of var 0..1: sameside; % 互相憎恶的客人是否坐在同一边
+array[Hatreds] of var Seats: cost; % 互相憎恶的客人的距离
+
+include "alldifferent.mzn";
+constraint alldifferent(pos);
+constraint forall(g in Males)( pos[g] mod 2 == 1 );
+constraint forall(g in Females)( pos[g] mod 2 == 0 );
+constraint not (pos[ed] in {1,6,7,12});
+constraint abs(pos[bride] - pos[groom]) <= 1 /\
+ (pos[bride] <= 6 <-> pos[groom] <= 6);
+constraint forall(h in Hatreds)(
+ p1[h] = pos[h1[h]] /\
+ p2[h] = pos[h2[h]] /\
+ sameside[h] = bool2int(p1[h] <= 6 <-> p2[h] <= 6) /\
+ cost[h] = sameside[h] * abs(p1[h] - p2[h]) +
+ (1 - sameside[h]) * (abs(13 - p1[h] - p2[h]) + 1) );
+
+solve maximize sum(h in Hatreds)(cost[h]);
+
+output [ show(g)++" " | s in Seats,g in Guests where fix(pos[g]) == s]
+ ++ ["\n"];
diff --git a/software/minizinc/docs/chi/examples/wedding2.mzn b/software/minizinc/docs/chi/examples/wedding2.mzn
new file mode 100644
index 0000000..c03d668
--- /dev/null
+++ b/software/minizinc/docs/chi/examples/wedding2.mzn
@@ -0,0 +1,29 @@
+enum Guests = { bride, groom, bestman, bridesmaid, bob, carol,
+ ted, alice, ron, rona, ed, clara};
+set of int: Seats = 1..12;
+set of int: Hatreds = 1..5;
+array[Hatreds] of Guests: h1 = [groom, carol, ed, bride, ted];
+array[Hatreds] of Guests: h2 = [clara, bestman, ted, alice, ron];
+set of Guests: Males = {groom, bestman, bob, ted, ron,ed};
+set of Guests: Females = {bride,bridesmaid,carol,alice,rona,clara};
+
+array[Guests] of var Seats: pos; % 客人的座位
+
+include "alldifferent.mzn";
+constraint alldifferent(pos);
+
+constraint forall(g in Males)( pos[g] mod 2 == 1 );
+constraint forall(g in Females)( pos[g] mod 2 == 0 );
+
+constraint not (pos[ed] in {1,6,7,12});
+constraint abs(pos[bride] - pos[groom]) <= 1 /\
+ (pos[bride] <= 6 <-> pos[groom] <= 6);
+
+solve maximize sum(h in Hatreds)(
+ let { var Seats: p1 = pos[h1[h]];
+ var Seats: p2 = pos[h2[h]];
+ var 0..1: same = bool2int(p1 <= 6 <-> p2 <= 6); } in
+ same * abs(p1 - p2) + (1-same) * (abs(13 - p1 - p2) + 1));
+
+output [ show(g)++" " | s in Seats,g in Guests where fix(pos[g]) == s]
+ ++ ["\n"];
diff --git a/software/minizinc/docs/chi/figures/MiniZn_logo_2.pdf b/software/minizinc/docs/chi/figures/MiniZn_logo_2.pdf
new file mode 100644
index 0000000..9bfec1f
--- /dev/null
+++ b/software/minizinc/docs/chi/figures/MiniZn_logo_2.pdf
@@ -0,0 +1,347 @@
+%PDF-1.5
%
+1 0 obj
<>/OCGs[5 0 R]>>/Pages 3 0 R/Type/Catalog>>
endobj
2 0 obj
<>stream
+
+
+
+
+ Adobe Illustrator CS5.1
+ 2016-01-12T13:55:45+11:00
+ 2016-01-12T13:55:45+11:00
+ 2016-01-12T13:55:45+11:00
+
+
+
+ 256
+ 256
+ JPEG
+ /9j/4AAQSkZJRgABAgEASABIAAD/7QAsUGhvdG9zaG9wIDMuMAA4QklNA+0AAAAAABAASAAAAAEA
AQBIAAAAAQAB/+4ADkFkb2JlAGTAAAAAAf/bAIQABgQEBAUEBgUFBgkGBQYJCwgGBggLDAoKCwoK
DBAMDAwMDAwQDA4PEA8ODBMTFBQTExwbGxscHx8fHx8fHx8fHwEHBwcNDA0YEBAYGhURFRofHx8f
Hx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8f/8AAEQgBAAEAAwER
AAIRAQMRAf/EAaIAAAAHAQEBAQEAAAAAAAAAAAQFAwIGAQAHCAkKCwEAAgIDAQEBAQEAAAAAAAAA
AQACAwQFBgcICQoLEAACAQMDAgQCBgcDBAIGAnMBAgMRBAAFIRIxQVEGE2EicYEUMpGhBxWxQiPB
UtHhMxZi8CRygvElQzRTkqKyY3PCNUQnk6OzNhdUZHTD0uIIJoMJChgZhJRFRqS0VtNVKBry4/PE
1OT0ZXWFlaW1xdXl9WZ2hpamtsbW5vY3R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo+Ck5SVlpeYmZ
qbnJ2en5KjpKWmp6ipqqusra6voRAAICAQIDBQUEBQYECAMDbQEAAhEDBCESMUEFURNhIgZxgZEy
obHwFMHR4SNCFVJicvEzJDRDghaSUyWiY7LCB3PSNeJEgxdUkwgJChgZJjZFGidkdFU38qOzwygp
0+PzhJSktMTU5PRldYWVpbXF1eX1RlZmdoaWprbG1ub2R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo
+DlJWWl5iZmpucnZ6fkqOkpaanqKmqq6ytrq+v/aAAwDAQACEQMRAD8A9U4qk/mXzXo/l2z+sahL
Rnr6Fum8shHZV/WTtmVpdJkzyqI+PQOLqtZjwRuR+HUvIfMP5u+ZdRdksGGmWv7KxfFKR/lSEf8A
EQM6XTdjYoby9Z+z5PMantrLPaPoH2/Nht3f314/O7uZbh+vKV2c/exObSGOMfpADq55JS+ok+9D
5Ng7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FURaX99ZvztLmW3fr
yidkP3qRkJ44y+oAs4ZJR+kke5mXl783fMunOqX7DU7X9pZfhlA/yZAP+JA5q9T2NinvH0H7Pk7T
TdtZYbS9Y+35vXvLXmvR/MVn9Y0+WrJT17d9pYyezL+ojbOa1WkyYJVIfHoXp9LrMeeNxPw6hOMx
XKSfzX5ls/Lujy6hcfGw+C3grQySn7Kj9ZPhmVpNLLPkER8fIOLrNVHBjMj8PMvnXWdZ1DWNQlv7
+Uy3Ep3P7Kr2VR2Udhnb4MEcURGI2eGz55ZZGUjZKBy1qTrSvJnmnVY1ksdNmlib7MrARofk8hVT
9+YubXYcZqUhf47nKw6HNkFxia/HemX/ACqrz7/1a/8Akvb/APVTKP5X03877Jfqcj+SNT/N+2P6
3f8AKqvPv/Vr/wCS9v8A9VMf5X03877JfqX+SNT/ADftj+t3/KqvPv8A1a/+S9v/ANVMf5X03877
JfqX+SNT/N+2P63f8qq8+/8AVr/5L2//AFUx/lfTfzvsl+pf5I1P837Y/rd/yqrz7/1a/wDkvb/9
VMf5X03877JfqX+SNT/N+2P63f8AKqvPv/Vr/wCS9v8A9VMf5X03877JfqX+SNT/ADftj+t3/Kqv
Pv8A1a/+S9v/ANVMf5X03877JfqX+SNT/N+2P63f8qq8+/8AVr/5L2//AFUx/lfTfzvsl+pf5I1P
837Y/rd/yqrz7/1a/wDkvb/9VMf5X03877JfqX+SNT/N+2P63f8AKqvPv/Vr/wCS9v8A9VMf5X03
877JfqX+SNT/ADftj+t3/KqvPv8A1a/+S9v/ANVMf5X03877JfqX+SNT/N+2P63f8qq8+/8AVr/5
L2//AFUx/lfTfzvsl+pf5I1P837Y/rUrv8tfO1pazXdxp3C3t42lmf1oDxRAWY0EhJoB2x/lfTfz
vsl+pf5I1P8AN+2P63l//Kz/ACN/1cv+SFx/1Tx/lfTfzvsl+pf5I1P837Y/rd/ys/yN/wBXL/kh
cf8AVPH+V9N/O+yX6l/kjU/zftj+t3/Kz/I3/Vy/5IXH/VPH+V9N/O+yX6l/kjU/zftj+t3/ACs/
yN/1cv8Akhcf9U8f5X03877JfqX+SNT/ADftj+t3/Kz/ACN/1cv+SFx/1Tx/lfTfzvsl+pf5I1P8
37Y/rd/ys/yN/wBXL/khcf8AVPH+V9N/O+yX6l/kjU/zftj+t3/Kz/I3/Vy/5IXH/VPH+V9N/O+y
X6l/kjU/zftj+t3/ACs/yN/1cv8Akhcf9U8f5X03877JfqX+SNT/ADftj+t3/Kz/ACN/1cv+SFx/
1Tx/lfTfzvsl+pf5I1P837Y/rd/ys/yN/wBXL/khcf8AVPH+V9N/O+yX6l/kjU/zftj+t3/Kz/I3
/Vy/5IXH/VPH+V9N/O+yX6l/kjU/zftj+tMdM84eWNTcR2WowySt9mJiY3PyWQKx+7L8Ouw5DUZC
/wAd7j5tDmxi5RNfjuTjMpxUdo2s6ho+oRX9hKYriI7H9ll7qw7qe4yrPgjliYyGzbgzyxSEomiH
0V5U8y2fmLR4tQt/gY/BcQVqY5R9pT+sHwziNXpZYMhifh5h7nR6qOfGJD4+ReQ/m75hfUfMrWCN
/oumD0lXsZWoZG/Uv0Z0vY2m4MXEec/u6PMdtanjy8I5Q+/qwXNu6h7D+Wv5a2kdpDrWtQiW5lAk
tLSQVSNDurup6seoB6fPpzPanakjI48ZoDmXp+y+y4iIyZBZPIPT8596F2KuxV2KuxV2KuxV2Kux
V2KuxV2KuxVKvNn/ACius/8AMDc/8mWxV+YGKuxV2KuxV2KuxV6JoH5Bfmlr/lE+atL0gzaYyNJb
oZEW4njQkM8MJPNhsad2/ZrtirzvFXYq7FXYq9E078gfzU1DycPN1po5fSmhN1CnqRi4kgA5erHC
TzK0FR3YbqDUYqrfl1+Yt1HdQ6PrExltpSI7W6kNWjY7KjseqnoCeny6dB2X2pISGPIbB5F5/tTs
uJicmMURzD1rOmeXZ1+UXmF9O8yrYO3+i6mPSZewlWpjb9a/Tmo7Z03Hi4hzh93V2/Yup4MvCeU/
v6MNv7t7y+ubt/t3ErytXxdix/Xm0xw4YiPcHV5J8UjLvNpl5M0qPVfNOm2Mi8opZg0q+KRgyOPp
VTlGuzHHhlIc6/Y36HCMmaMTyv8Aa+ls4N752KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KpV5s/wCU
V1n/AJgbn/ky2KvzAxV2KvvjyN+RH5cS/lvottqvl2xl1W40uD67fGBDP680IMjiQjlyVmNDir4S
1fTLrStWvdLu143VhPLbXC9KSQuUcfeuKvsv/nHf8l/JFx+VOk6l5j0Cy1HU9UMt4ZruBJHWJ3Kw
qGYE8TGit/ssVfK35teXYvLn5l+ZdGgjWK2tb+Y2sSjiqQSt6sKgD+WN1GKvavy//wCcurDyz+XN
j5futCmudZ0m2FrZSxyIttKsYpE0tfjSgoGCg1p2rsq+bJ5nnnkmk+3KxdqbCrGpxVYQQaEUPgcV
RL6VqiWS3z2c62TUC3RjcREnpRyOP44qhcVfTflv/nMO30j8uLTRH0SWTzJp9ktjbXIaMWjejGIo
pnB+MGgBZAtCe4rsq+ZMVfRnk/U31Pyxp17IeUskIWVvF4yY2P0spzvNDmOTDGR51+x4HXYRjzSi
OV/tZBYXb2d9bXafbt5UlWnijBh+rL8kOKJj3hoxz4ZCXcbQ+TYMs/Kr/lPdL/57/wDUPJmu7X/x
aXw/3Qdl2R/jMfj/ALkvoTOKe2dirsVdirsVdirsVdirsVdirsVdirsVdiqVebP+UV1n/mBuf+TL
Yq/MDFU18q6M+ueZ9I0ZBV9Svbe0H/PeVY+3+tir9LrjWdOsdW07RpCI7jUY52skFACLUIXUD/Ve
v0Yq+I/+cjvIlzbfnvPYWMe/miS1ubFKHeW8YQv8+Vwrn6cVfaVtPo3lm38u+Wkbh66jTdLiFASt
naPL0r0WK37e2Kvjf/nMLRPqH5utfAfDq+n21yWH88fK2IPvxgXFXv8A+Rnl7QLj8hdEubjTLSa4
eyui00kEbOSJpgCWKk9sVfLv/OPOp+RLP8xrCDzhpMepW986W1hPMeUVtdO3GOSSE/u5FYnj8X2f
tdsVfZ2q/k9+W175zHnfU9Lhl1SCEKxm4/VqxbrcSREcGkRRQM3QAdwCFUR5X/NH8tPOmoX2g6Bq
1vqtzaRsbu0WOTgYQwjYoZEWOWOrAEoWG48cVfHf/OUP5eaL5L/MZU0SJbbTdXtVv0s02SGRpHjk
RB2QlOQHatBsBir6a8ieXfL8n5BaVcyaZaPct5eDtM0EZcv9VJ5Fita174q+BcVe9/lh/wAoNpv/
AD3/AOoiTO17I/xaPx/3ReJ7X/xmXw/3IZTmxda7FWWflV/ynul/89/+oeTNd2v/AItL4f7oOy7I
/wAZj8f9yX0JnFPbOxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxVKvNn/KK6z/zA3P/ACZbFX5gYq9T
/wCcY9D/AEt+dOgBk5Q2Jmvpfb0IWMZ/5GlMVe8/85B+fP8ADP5zflnOZOEOnvPNeGtALe/kS1lJ
+Ucb4q9F88/lpH5g/MvyN5pKKYvL8t0b3+ZgYvUtT/zznWv04q86/Njz76P/ADkt+XWiRSUi0yQC
cA0/favW24tQjf0+NP8AW98VST/nODROVl5W1xF/upLmxmfx9RUliH0enJir078hP/WfdC/5gbr/
AJPTYq+C9IJGrWRGxE8VD/sxir7z/wCcotSvrD8lddezmaB5zbW8joaExS3CLIlfBlJU+2Kvnb/n
Db/ybk3/AGyrn/k7Diqa/wDObX/KfaF/2yh/1Ey4q+gPIH/rPWk/+A4P+oU4q/PXFXvf5Yf8oNpv
/Pf/AKiJM7Xsj/Fo/H/dF4ntf/GZfD/chlObF1rsVZZ+VX/Ke6X/AM9/+oeTNd2v/i0vh/ug7Lsj
/GY/H/cl9CZxT2zsVdirsVdirsVdirsVdirsVdirsVdirsVUry1iu7Se0mFYbiNopBturqVPWvY4
q/MDzBol9oOu6hot+vC8064ktZxQj4omKkivY0qPbFX0D/zhHo8c3nDzFq7cS1lYR2yAkVBupuZI
HytqV9/fFWP/APOYep/W/wA3zb1207TbW2p/rGS48B/v/FX1n+UHmk+afyz8u62787i4s447tq1r
cQfuZj9MkbHFXw35z8+/pT87bzzisvKGLWY7i0lBr/o9nKqwHb/iqJcVfV//ADlro6ah+TN9Oaep
pd3a3kQPUn1Pq7U/2E7H5YqmH5Cf+s+6F/zA3X/J6bFXwXpP/HVsv+M8X/Exir7q/wCcsP8AySWs
f8Z7P/qJjxV8/wD/ADht/wCTcm/7ZVz/AMnYcVTX/nNr/lPtC/7ZQ/6iZcVfQHkD/wBZ60n/AMBw
f9QpxV+euKve/wAsP+UG03/nv/1ESZ2vZH+LR+P+6LxPa/8AjMvh/uQynNi612Kss/Kr/lPdL/57
/wDUPJmu7X/xaXw/3Qdl2R/jMfj/ALkvoTOKe2dirsVdirsVdirsVdirsVdirsVdirsVdirsVfN3
/OT/APzj/f8AmOZvO3lS3M+sIgXV9NjHx3KRrRZoh+1KigKV/aFKbihVfIAM9vMacoZ4mIPVXVhs
fAg4q3dXV1dztPdTPPO9OcsrF3PEBRVmJOwFMVUsVdiqvd399eyereXEtzKBTnM7SNQbUqxOKqGK
uxV2KuxV2KuxV2Kve/yw/wCUG03/AJ7/APURJna9kf4tH4/7ovE9r/4zL4f7kMpzYutdirLPyq/5
T3S/+e//AFDyZru1/wDFpfD/AHQdl2R/jMfj/uS+hM4p7Z2KvI/+ckb28tPKumPazyW7tfUZonZC
R6LmhKkYq+ef0/rv/Vyuv+R0n/NWBXfp/Xf+rldf8jpP+asVd+n9d/6uV1/yOk/5qxV36f13/q5X
X/I6T/mrFXfp/Xf+rldf8jpP+asVd+n9d/6uV1/yOk/5qxV36f13/q5XX/I6T/mrFXfp/Xf+rldf
8jpP+asVd+n9d/6uV1/yOk/5qxVdHrfmGWRYo9Qu3kchURZpCSxNAAK98KvsLyL5fn0Dyrp+mXUz
XF5FHyvJnYuWmkPJ/iJNQpPEewxVPsVdirCPOv5K/ll5zma617Q4Zb9ut/AXt7g+7SQlC/8As64q
wz/oUL8m/wDlmvv+ktv6Yq7/AKFC/Jv/AJZr7/pLb+mKu/6FC/Jv/lmvv+ktv6Yq7/oUL8m/+Wa+
/wCktv6Yq7/oUL8m/wDlmvv+ktv6Yq7/AKFC/Jv/AJZr7/pLb+mKu/6FC/Jv/lmvv+ktv6Yq7/oU
L8m/+Wa+/wCktv6Yq7/oUL8m/wDlmvv+ktv6Yq7/AKFC/Jv/AJZr7/pLb+mKu/6FC/Jv/lmvv+kt
v6YqwvzF5Q0byfrFx5c0VZE0yx4fV1lcyOPWRZnqx6/HIc7Xsj/Fo/H/AHReJ7X/AMZl8P8AchLc
2LrXYqyz8qv+U90v/nv/ANQ8ma7tf/FpfD/dB2XZH+Mx+P8AuS+hM4p7Z2KvHf8AnJv/AJRPSv8A
mPH/ACZkxV84YFdirsVdirsVdirsVdirsVen/kB5P/TXnAapcJWx0QCc1FQ1w1RCv+xoX/2Iwq+o
sVdirsVdirsVdirsVdirsVdirsVdirsVdirsVfPf5q/8p7qn/PD/AKh487Xsj/Fo/H/dF4ntf/GZ
fD/chiebF1rsVZZ+VX/Ke6X/AM9/+oeTNd2v/i0vh/ug7Lsj/GY/H/cl9CZxT2zsVeO/85N/8onp
X/MeP+TMmKvnDArsVdirsVdirsVdirsVd1xV9f8A5S+T/wDC3kqztJU4X91/pd/XqJZQPgP+ogVf
mMKsyxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV89/mr/AMp7qn/PD/qHjzteyP8AFo/H/dF4
ntf/ABmXw/3IYnmxda7FWWflV/ynul/89/8AqHkzXdr/AOLS+H+6DsuyP8Zj8f8Acl9CZxT2zsVS
TzX5M8v+a7OGz1uBp7eCT1o1WR4yH4la1Qg9GxVi3/Kgvyx/6t0v/STP/wA1Yq7/AJUF+WP/AFbp
f+kmf/mrFXf8qC/LH/q3S/8ASTP/AM1Yq7/lQX5Y/wDVul/6SZ/+asVd/wAqC/LH/q3S/wDSTP8A
81Yq+bvOy+X4/NOoQeX4jFpFvKYbartIX9P4Wfk5JozAke2BUjxV2Ks//JTyd/iTzrbvPHz07S6X
l3X7JKn91Gf9Z+3cA4VfWWKuxVpmVFLuQqqCWYmgAHUk4qw23/N7yFc+ZU8vW+oiS6kPBLlR/oxl
7RCWtCx7U+E9K12xVmeKuxV2Ksc80fmJ5O8sArq+oxxXIFRZx1lnNRUfu0qRXxag98Veaar/AM5P
aXG5XStEmuU6CW5mWD6eCLN/xLFUuX/nKG8DDl5ejK9wLpgafP0jirI9E/5yT8n3jrHqlnc6YzdZ
aC4iHzZOMn3Jir07R9d0bWrMXmk3kV7bHb1IXDUPgwG6n2O+Ko7FXYq7FXYq+e/zV/5T3VP+eH/U
PHna9kf4tH4/7ovE9r/4zL4f7kMTzYutdirLPyq/5T3S/wDnv/1DyZru1/8AFpfD/dB2XZH+Mx+P
+5L6EzintnYq7FXYq7FXYq7FWD/nH5v/AMNeSLuWF+OoX/8AodlQ0YNKDzcU/kSpB8aYq+RsCuxV
2Kvq/wDI7yePL3kqCeePjqOr0u7knqEYfuU/2KGtPFjhV6FirEPPH5peVfKETJez/WNSpWPTbchp
jUbF+0a+7fQDir5z89/m35r83M8E8v1LSSfh063JCEDp6rbNIfnt4AYqwnpgV9K/kd+ah120Xy5r
M3LWbVP9EuHO9zCg6E95EHX+Yb9a4Veo6tq+maPp82o6ncpaWUA5SzSGgHgB3JPYDc4q+ePzC/5y
A1jVWksPLBfTNO3VrzpdSj/JI/uh/q/F7jpiryKSSSWRpJWLyOSzuxJYk9SSeuBVuKuxV2Kpn5e8
y655e1BNQ0e7e0uV6lD8Lr/K6H4WX2IxV9Qflb+a2n+dLRredVtNdtkDXNqCeEiigMsVd+NTup3X
8cKs+xV2KuxV89/mr/ynuqf88P8AqHjzteyP8Wj8f90Xie1/8Zl8P9yGJ5sXWuxVln5Vf8p7pf8A
z3/6h5M13a/+LS+H+6DsuyP8Zj8f9yX0JnFPbOxV2KuxV2KuxV2Kvln8+/N/6c85vp8EnKw0UG2Q
A1Uzk1nb/ggE/wBjirzTArsVZd+VflA+afOllYSJysYD9a1CvT0IiCVP+uxCfThV9hgAAACgHQYq
snhWaCSFmZVlVkLRsUcBhSqspDKfAjFXyl+a/wCVmq+Ub9r5JJL/AEW7cmO+f4pEdiT6c5/m8G/a
/DFXn2BXYqiNP1C806+gv7KVoLu2dZYJV6q6moOKsg88/mL5i85XccupyBLeAAQWUNVhQ03fiSas
fE/LphVi+BXYq7FXYq7FXYqjtC1vUND1e11bTpDFeWjiSJux7FW8VYVDDuMVfZ3lbzDaeYvL1hrV
ptDexByla8HHwyIfdHBXCqa4q7FXz3+av/Ke6p/zw/6h487Xsj/Fo/H/AHReJ7X/AMZl8P8Achie
bF1rsVZZ+VX/ACnul/8APf8A6h5M13a/+LS+H+6DsuyP8Zj8f9yX0JnFPbOxV2KuxV2KuxVjX5je
bE8reUL/AFaoFyqelYqd63Enwx7dwv2j7A4q+NHd5HZ3Ys7kszHcknck4FaxV2Kvp/8A5x88n/of
yidYuEpe60RKtRutslREN/5ql/cEYVepYq7FULqmmWOqafcadfwrPZ3SGOeJuhU/qPge2Kvj78xP
JV15P8zXGlSFpLY/vbG4YU9SBvsn/WU1VvcYqxnArsVdirsVdirJtJ/LTz7q0AuLDQ7qSBhySV1E
SsPFTKUDfRiqB13yf5o0DidY0y4skY8UlkQ+mx8FkFUJ+RxVJ8VdirsVfRf/ADjLq8k/l7VtKdiw
sblJowf2VuVIoP8AZQk/ThV7NirsVfPf5q/8p7qn/PD/AKh487Xsj/Fo/H/dF4ntf/GZfD/chieb
F1rsVZZ+VX/Ke6X/AM9/+oeTNd2v/i0vh/ug7Lsj/GY/H/cl9CZxT2zsVdirsVdirsVfNv8Azkb5
v/SHmG38u2z1tdJXnc06G5lFaH/Ujp9JOKvIMCuxVkPkHyrL5p82WGjrUQzPzu5F/Ygj+KQ17fCK
D3IxV9mwwxQwpDCgjiiUJGiigVVFAAPADCq/FXYq7FXlP/ORXllNR8mx6xGlbrR5QzMOvoTkRuP+
D4H78VfMmBXYq7FVS3t57m4jt7eNpZ5mEcUSCrMzGiqAO5OKvpr8q/yV03y9bw6prsKXmvuA6xtR
4ravRVH2WkHd+37PiSr1PFUPqOnWOpWM1hfwJc2dwpSaGQVVlP8An1xV8bef/LB8sebtS0UEtDby
crZ26mGRRJHU9yFYA++BWP4q7FXuP/OL3+9/mH/jFbf8Skwq+gMVdir57/NX/lPdU/54f9Q8edr2
R/i0fj/ui8T2v/jMvh/uQxPNi612Kss/Kr/lPdL/AOe//UPJmu7X/wAWl8P90HZdkf4zH4/7kvoT
OKe2dirsVdirsVSnzZ5itfLnly/1q5oUs4i6oTTnIfhjT/ZuQMVfFd/fXV/fXF9duZbq6keaeQ9W
d2LMfvOBVDFXYq+jv+ccfJ/1HQ7nzLcpxudTJhtK9RbRndv+ekg+5RhV7HirsVdirsVSXzrYpf8A
k/W7NwCJrG4Va9m9Jip+hqHFXxRgV2KuxV73/wA47/l6npnzhqUVXJaLSEcdAPhkn/Wi/T7YVe7Y
q7FXYq+ZP+ckoEi8/wBu69Z9OhkbbuJZU/UmKvKcCuxV7j/zi9/vf5h/4xW3/EpMKvoDFXYq+e/z
V/5T3VP+eH/UPHna9kf4tH4/7ovE9r/4zL4f7kMTzYutdirLPyq/5T3S/wDnv/1DyZru1/8AFpfD
/dB2XZH+Mx+P+5L6EzintnYq7FXYq7FXgX/OSnm/nPZeVbZ/hipeahQ/tMCIUPyWrH5rirwvArsV
TXyp5eu/MXmKw0a1B9S8lCMw/YjHxSOfZEBbFX2pp1ha6dYW1haJ6draRJDBGOyRqFUfcMKojFXY
q7FXYqh9RAbT7pWFQYpAQehHE4q+FsCuxV2KvtL8v1VfIflwKAB+jLM0G25t0J/HCqf4q7FXYq+a
P+cmP+U7sP8Atlxf9RFxiryXArsVe4/84vf73+Yf+MVt/wASkwq+gMVdir57/NX/AJT3VP8Anh/1
Dx52vZH+LR+P+6LxPa/+My+H+5DE82LrXYqyz8qv+U90v/nv/wBQ8ma7tf8AxaXw/wB0HZdkf4zH
4/7kvoTOKe2dirsVdiqE1fVLTStLu9TvG4WtnE88zd+KDkae57Yq+KfMOt3mu63e6veH/SL2VpXA
6KCfhQeyrRRgVL8Vdir33/nGvyfwgvfNd0nxS1tNOJ7KprM4+bUUH2bCr3TFXYq7FXYq7FVDUP8A
eC5/4xP/AMROKvhXArsVdir7T8gf8oJ5c/7Zdl/1DphVPsVdirsVfNH/ADkx/wAp3Yf9suL/AKiL
jFXkuBXYq9x/5xe/3v8AMP8Axitv+JSYVfQGKuxV89/mr/ynuqf88P8AqHjzteyP8Wj8f90Xie1/
8Zl8P9yGJ5sXWuxVln5Vf8p7pf8Az3/6h5M13a/+LS+H+6DsuyP8Zj8f9yX0JnFPbOxV2KuxV4t/
zkj5v+q6TaeWLZ/31+Rc3wB3EEbfu1P+vIK/7HFXzvgV2KozRtJvNX1az0uzXldXsyQRA9OTmlT7
DqfbFX2t5f0W00PRLLSLMUt7KFYUNKFuI+Jz7s1WPvhVH4q7FXYq7FXYqoah/vBc/wDGJ/8AiJxV
8K4FdirsVfafkD/lBPLn/bLsv+odMKp9irsVdir5o/5yY/5Tuw/7ZcX/AFEXGKvJcCuxV7j/AM4v
f73+Yf8AjFbf8Skwq+gMVdir57/NX/lPdU/54f8AUPHna9kf4tH4/wC6LxPa/wDjMvh/uQxPNi61
2Kss/Kr/AJT3S/8Anv8A9Q8ma7tf/FpfD/dB2XZH+Mx+P+5L6EzintnYq7FVlxcQ28ElxO4jghRp
JZGNAqKKsxPgAMVfF/nnzRP5n803+sycglxIRbRt1SBPhiX6FG/vgVIcVdir23/nG3yf6+oXfmm5
T91aA2thUdZXFZXH+qh4/wCyOFX0JirsVdirsVdirsVUNQ/3guf+MT/8ROKvhXArsVdir7T8gf8A
KCeXP+2XZf8AUOmFU+xV2KuxV80f85Mf8p3Yf9suL/qIuMVeS4Fdir3H/nF7/e/zD/xitv8AiUmF
X0BirsVfPf5q/wDKe6p/zw/6h487Xsj/ABaPx/3ReJ7X/wAZl8P9yGJ5sXWuxVln5Vf8p7pf/Pf/
AKh5M13a/wDi0vh/ug7Lsj/GY/H/AHJfQmcU9s7FXYq8r/5yF83/AKI8pJo1u/G81pjG9Oq20dDK
fbkSq+4JxV8xYFdirsVemeVvz21zy1oNpoun6VZG2tFIDv6vN2YlmdqOBVmJwqm3/Qzfmz/q1WH3
Tf8AVTFXf9DN+bP+rVYfdN/1UxV3/Qzfmz/q1WH3Tf8AVTFXf9DN+bP+rVYfdN/1UxV3/Qzfmz/q
1WH3Tf8AVTFU78lfn95k1/zVpmj3OnWcUF7MIpJI/V5gEE1HJyO2KvbdQ/3guf8AjE//ABE4q+Fc
CuxV2KvtPyB/ygnlz/tl2X/UOmFU+xV2KuxV80f85Mf8p3Yf9suL/qIuMVeS4Fdir3H/AJxe/wB7
/MP/ABitv+JSYVfQGKuxV89/mr/ynuqf88P+oePO17I/xaPx/wB0Xie1/wDGZfD/AHIYnmxda7FW
WflV/wAp7pf/AD3/AOoeTNd2v/i0vh/ug7Lsj/GY/H/cl9CZxT2zsVcSACSaAdTir48/NXzd/inz
pe38T87GE/VbDw9GIkBh/rsS/wBOKsRwK7FXYq7FXYq7FXYq7FXYqy38pv8AyY+gf8xS/wDEThV9
e6h/vBc/8Yn/AOInFXwrgV2KuxV9p+QP+UE8uf8AbLsv+odMKp9irsVdir5o/wCcmP8AlO7D/tlx
f9RFxiryXArsVe4/84vf73+Yf+MVt/xKTCr6AxV2Kvnv81f+U91T/nh/1Dx52vZH+LR+P+6LxPa/
+My+H+5DE82LrXYqyz8qv+U90v8A57/9Q8ma7tf/ABaXw/3Qdl2R/jMfj/uS+hM4p7Z2KvP/AM7v
N/8Ah3yTcRwPx1DVa2drQ0ZVYfvZB/qptXsSMVfJ2BXYq7FXYq7FXYq7FXYq7FXYqy38pv8AyY+g
f8xS/wDEThV9e6h/vBc/8Yn/AOInFXwrgV2KuxV9p+QP+UE8uf8AbLsv+odMKp9irsVdir5o/wCc
mP8AlO7D/tlxf9RFxiryXArsVe4/84vf73+Yf+MVt/xKTCr6AxV2Kvnv81f+U91T/nh/1Dx52vZH
+LR+P+6LxPa/+My+H+5DE82LrXYqyz8qv+U90v8A57/9Q8ma7tf/ABaXw/3Qdl2R/jMfj/uS+hM4
p7Z2KvJfzW/Kfzb521+K7g1C0t9OtIRFaW8pl5At8UjtxRhVm269AMVYV/0LJ5s/6uth983/AFTx
V3/Qsnmz/q62H3zf9U8Vd/0LJ5s/6uth983/AFTxV3/Qsnmz/q62H3zf9U8Vd/0LJ5s/6uth983/
AFTxV3/Qsnmz/q62H3zf9U8Vd/0LJ5s/6uth983/AFTxV3/Qsnmz/q62H3zf9U8Vd/0LJ5s/6uth
983/AFTxV3/Qsnmz/q62H3zf9U8VTvyV+QPmTQPNWmaxc6jZywWUwlkjj9XmQARQckA74q9wuYjL
bSxKaGRGUE9KsKYq+dP+hZPNn/V1sPvm/wCqeKu/6Fk82f8AV1sPvm/6p4q7/oWTzZ/1dbD75v8A
qnir33y1pk2leXNK0uZ1kmsLO3tZHSvFmhiVCVrQ0JXFUyxV2KuxV5N+bX5Pa5508x22qWF7bW0M
NmlqyT+pyLJLI5I4KwpSQYqwn/oWTzZ/1dbD75v+qeKu/wChZPNn/V1sPvm/6p4q9D/J/wDK3WPJ
FzqcuoXdvci+SJYxb86qYy5PLmq/zYq9MxV2Kvnv81f+U91T/nh/1Dx52vZH+LR+P+6LxPa/+My+
H+5DE82LrXYqyz8qv+U90v8A57/9Q8ma7tf/ABaXw/3Qdl2R/jMfj/uS+hM4p7Z2KuxV2KuxV2Ku
xV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2Kvnv81f+U91T/nh/wBQ8edr
2R/i0fj/ALovE9r/AOMy+H+5DE82LrXYqyz8qv8AlPdL/wCe/wD1DyZru1/8Wl8P90HZdkf4zH4/
7kvoTOKe2dirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdi
r57/ADV/5T3VP+eH/UPHna9kf4tH4/7ovE9r/wCMy+H+5DE82LrXYqyz8qv+U90v/nv/ANQ8ma7t
f/FpfD/dB2XZH+Mx+P8AuS+hM4p7Z2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2K
uxV2KuxV2KuxV2KuxV2Kvnv81f8AlPdU/wCeH/UPHna9kf4tH4/7ovE9r/4zL4f7kMTzYutRF/aP
Z31zaP8Abt5XiavijFT+rIY58URLvDPJDhkY9xpMvJmqx6V5p02+kbjFFMFlbwSQGNz9Csco12E5
MMojnX7W/Q5hjzRkeV/sfS2cG987FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXYq7FXY
q7FXYq7FXYq7FXYq7FXzT5z1WPVfNOpX0bcopZisTeKRgRofpVRneaHCceGMTzr9rwOuzDJmlIcr
/YlthaPeX1taJ9u4lSJaeLsFH68vyT4YmXcGjHDikI95pmX5u+Xn07zK1+i/6LqY9VW7CVaCRf1N
9OavsbU8eLhPOH3dHadtabgy8Q5T+/qwXNu6h7D+Wv5lWklpDoutTCK5iAjtLuQ0SRBsqOx6MOgJ
6/PrzPanZchI5MYsHmHp+y+1ImIx5DRHIvT8596F2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2KuxV2
KuxV2KuxV2KuxV2KuxV2KuxV2KvMPzK/Mq0jtJtF0WYS3MoMd3dxmqRodmRGHVj0JHT59Og7L7Lk
ZDJkFAcg892p2pEROPGbJ5l49nTPMM6/KLy8+o+ZVv3X/RdMHqs3YytURr+tvozUds6ngxcI5z+7
q7fsXTceXiPKH39Hr3mvy1Z+YtHl0+4+Bj8dvPSpjlH2WH6iPDOa0mqlgyCQ+PmHp9ZpY58Zifh5
F866zo2oaPqEthfxGK4iO4/ZZezKe6nsc7fBnjliJROzw2fBLFIxkKIQOWtSdaV5z806VGsdjqU0
US/ZiYiRB8kkDKPuzFzaHDkNyiL/AB3OVh12bGKjI1+O9Mv+Vq+ff+rp/wAkLf8A6p5R/JGm/m/b
L9bkfyvqf532R/U7/lavn3/q6f8AJC3/AOqeP8kab+b9sv1r/K+p/nfZH9Tv+Vq+ff8Aq6f8kLf/
AKp4/wAkab+b9sv1r/K+p/nfZH9Tv+Vq+ff+rp/yQt/+qeP8kab+b9sv1r/K+p/nfZH9Tv8Alavn
3/q6f8kLf/qnj/JGm/m/bL9a/wAr6n+d9kf1O/5Wr59/6un/ACQt/wDqnj/JGm/m/bL9a/yvqf53
2R/U7/lavn3/AKun/JC3/wCqeP8AJGm/m/bL9a/yvqf532R/U7/lavn3/q6f8kLf/qnj/JGm/m/b
L9a/yvqf532R/U7/AJWr59/6un/JC3/6p4/yRpv5v2y/Wv8AK+p/nfZH9Tv+Vq+ff+rp/wAkLf8A
6p4/yRpv5v2y/Wv8r6n+d9kf1O/5Wr59/wCrp/yQt/8Aqnj/ACRpv5v2y/Wv8r6n+d9kf1O/5Wr5
9/6un/JC3/6p4/yRpv5v2y/Wv8r6n+d9kf1O/wCVq+ff+rp/yQt/+qeP8kab+b9sv1r/ACvqf532
R/U7/lavn3/q6f8AJC3/AOqeP8kab+b9sv1r/K+p/nfZH9Tv+Vq+ff8Aq6f8kLf/AKp4/wAkab+b
9sv1r/K+p/nfZH9Tv+Vq+ff+rp/yQt/+qeP8kab+b9sv1r/K+p/nfZH9Tv8Alavn3/q6f8kLf/qn
j/JGm/m/bL9a/wAr6n+d9kf1O/5Wr59/6un/ACQt/wDqnj/JGm/m/bL9a/yvqf532R/U7/lavn3/
AKun/JC3/wCqeP8AJGm/m/bL9a/yvqf532R/U7/lavn3/q6f8kLf/qnj/JGm/m/bL9a/yvqf532R
/U7/AJWr59/6un/JC3/6p4/yRpv5v2y/Wv8AK+p/nfZH9Tv+Vq+ff+rp/wAkLf8A6p4/yRpv5v2y
/Wv8r6n+d9kf1O/5Wr59/wCrp/yQt/8Aqnj/ACRpv5v2y/Wv8r6n+d9kf1O/5Wr59/6un/JC3/6p
4/yRpv5v2y/Wv8r6n+d9kf1JbqvnPzTqsbR32pTSxN9qJSI0PzSMKp+7L8Ohw4zcYi/x3uPm12bI
KlI1+O5JcynFR2jaNqGsahFYWERluJTsP2VXuzHso7nKs+eOKJlI7NuDBLLIRiLJfRXlTy1Z+XdH
i0+3+Nh8dxPShklP2mP6gPDOI1eqlnyGR+HkHudHpY4MYiPj5lOMxXKSfzL5U0fzFZ/V9QiqyV9C
4TaWMnurfrB2zK0uryYJXE/DoXF1Wjx541IfHqHkPmH8ovMunOz2CjU7X9lovhlA/wAqMn/iJOdL
pu2cU9peg/Z83mNT2LlhvH1j7fkw27sL6zfhd20tu/TjKjIfuYDNpDJGX0kF1c8co/UCPeh8mwdi
rsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdirsVdiqItLC+vH4WltLcP04xIzn
7lByE8kY/UQGcMcpfSCfczLy9+UXmXUXV79Rplr+00vxSkf5MYP/ABIjNXqe2cUNo+s/Z83aabsX
LPeXoH2/J695a8qaP5ds/q+nxUZ6evcPvLIR3Zv1AbZzWq1eTPK5H4dA9PpdHjwRqI+PUpxmK5T/
AP/Z
+
+
+
+
+
+ 1
+ False
+ False
+
+ 1024.000000
+ 1024.000000
+ Pixels
+
+
+
+ Cyan
+ Magenta
+ Yellow
+ Black
+
+
+
+
+
+ Default Swatch Group
+ 0
+
+
+
+ R=0 G=175 B=250
+ RGB
+ PROCESS
+ 20
+ 145
+ 235
+
+
+ C=0 M=0 Y=0 K=85
+ RGB
+ PROCESS
+ 74
+ 74
+ 73
+
+
+
+
+
+
+
+
+ application/pdf
+
+
+ MiniZn_logo_2
+
+
+
+
+ proof:pdf
+ xmp.did:04801174072068118083B6E47DB0BE2A
+ uuid:ca3c4c8b-e42b-c649-bb42-cc264f779adc
+ xmp.did:F87F1174072068118083E4EBBD2E7794
+
+ xmp.iid:01801174072068118083B6E47DB0BE2A
+ xmp.did:01801174072068118083B6E47DB0BE2A
+ xmp.did:F87F1174072068118083E4EBBD2E7794
+ proof:pdf
+
+
+
+
+ saved
+ xmp.iid:F87F1174072068118083E4EBBD2E7794
+ 2015-07-09T14:32:47+10:00
+ Adobe Illustrator CS5.1
+ /
+
+
+ saved
+ xmp.iid:FD7F1174072068118083E4EBBD2E7794
+ 2015-07-09T14:38:28+10:00
+ Adobe Illustrator CS5.1
+ /
+
+
+ saved
+ xmp.iid:01801174072068118083FE633FCFE054
+ 2016-01-12T13:38:36+11:00
+ Adobe Illustrator CS5.1
+ /
+
+
+ saved
+ xmp.iid:01801174072068118083B6E47DB0BE2A
+ 2016-01-12T13:41:56+11:00
+ Adobe Illustrator CS5.1
+ /
+
+
+ saved
+ xmp.iid:04801174072068118083B6E47DB0BE2A
+ 2016-01-12T13:55:43+11:00
+ Adobe Illustrator CS5.1
+ /
+
+
+
+
+
+ Adobe PDF library 9.90
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
endstream
endobj
3 0 obj
<>
endobj
7 0 obj
<>/Resources<>/Properties<>>>/Thumb 11 0 R/TrimBox[0.0 0.0 1024.0 1024.0]/Type/Page>>
endobj
8 0 obj
<>stream
+HVK7Z((8,rF,z~T!hK|%Hos?xKȑrc3 sx?@撤pzjPZRC[2W5U[O-x@SoX#N-XU6t=S2@SRsq:}o~q8w+|
+vssU-5W\)-rX+