this repo has no description
at develop 80 kB view raw
1/* 2 * Main authors: 3 * Kevin Leo <kevin.leo@monash.edu> 4 * Andrea Rendl <andrea.rendl@nicta.com.au> 5 * Guido Tack <guido.tack@monash.edu> 6 */ 7 8/* This Source Code Form is subject to the terms of the Mozilla Public 9 * License, v. 2.0. If a copy of the MPL was not distributed with this 10 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 11 12#include <minizinc/eval_par.hh> 13#include <minizinc/solvers/gecode/fzn_space.hh> 14#include <minizinc/solvers/gecode/gecode_constraints.hh> 15#include <minizinc/solvers/gecode_solverinstance.hh> 16 17using namespace Gecode; 18 19namespace MiniZinc { 20namespace GecodeConstraints { 21 22void p_distinct(SolverInstanceBase& s, const Call* call) { 23 auto& gi = static_cast<GecodeSolverInstance&>(s); 24 IntVarArgs va = gi.arg2intvarargs(call->arg(0)); 25 MZ_IntConLevel icl = GecodeSolverInstance::ann2icl(call->ann()); 26 unshare(*gi.currentSpace, va); 27 distinct(*gi.currentSpace, va, icl == MZ_ICL_DEF ? MZ_ICL_DOM : icl); 28} 29 30void p_distinct_offset(SolverInstanceBase& s, const Call* call) { 31 auto& gi = static_cast<GecodeSolverInstance&>(s); 32 IntVarArgs va = gi.arg2intvarargs(call->arg(1)); 33 unshare(*gi.currentSpace, va); 34 IntArgs oa = GecodeSolverInstance::arg2intargs(call->arg(0)); 35 MZ_IntConLevel icl = GecodeSolverInstance::ann2icl(call->ann()); 36 distinct(*gi.currentSpace, oa, va, icl == MZ_ICL_DEF ? MZ_ICL_DOM : icl); 37} 38 39void p_all_equal(SolverInstanceBase& s, const Call* call) { 40 auto& gi = static_cast<GecodeSolverInstance&>(s); 41 IntVarArgs va = gi.arg2intvarargs(call->arg(0)); 42 rel(*gi.currentSpace, va, IRT_EQ, GecodeSolverInstance::ann2icl(call->ann())); 43} 44 45void p_int_cmp(GecodeSolverInstance& s, IntRelType irt, const Call* ce) { 46 const Annotation& ann = ce->ann(); 47 Expression* lhs = ce->arg(0); 48 Expression* rhs = ce->arg(1); 49 if (lhs->type().isvarint()) { 50 if (rhs->type().isvarint()) { 51 rel(*s.currentSpace, s.arg2intvar(lhs), irt, s.arg2intvar(rhs), 52 GecodeSolverInstance::ann2icl(ann)); 53 } else { 54 rel(*s.currentSpace, s.arg2intvar(lhs), irt, 55 static_cast<int>(rhs->cast<IntLit>()->v().toInt()), GecodeSolverInstance::ann2icl(ann)); 56 } 57 } else { 58 rel(*s.currentSpace, s.arg2intvar(rhs), swap(irt), 59 static_cast<int>(lhs->cast<IntLit>()->v().toInt()), GecodeSolverInstance::ann2icl(ann)); 60 } 61} 62 63void p_int_eq(SolverInstanceBase& s, const Call* call) { 64 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_EQ, call); 65} 66void p_int_ne(SolverInstanceBase& s, const Call* call) { 67 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_NQ, call); 68} 69void p_int_ge(SolverInstanceBase& s, const Call* call) { 70 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GQ, call); 71} 72void p_int_gt(SolverInstanceBase& s, const Call* call) { 73 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GR, call); 74} 75void p_int_le(SolverInstanceBase& s, const Call* call) { 76 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LQ, call); 77} 78void p_int_lt(SolverInstanceBase& s, const Call* call) { 79 p_int_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LE, call); 80} 81void p_int_cmp_reif(GecodeSolverInstance& s, IntRelType irt, ReifyMode rm, const Call* call) { 82 const Annotation& ann = call->ann(); 83 if (rm == RM_EQV && !call->arg(2)->type().isvar()) { 84 if (call->arg(2)->cast<BoolLit>()->v()) { 85 p_int_cmp(s, irt, call); 86 } else { 87 p_int_cmp(s, neg(irt), call); 88 } 89 return; 90 } 91 if (call->arg(0)->type().isvarint()) { 92 if (call->arg(1)->type().isvarint()) { 93 rel(*s.currentSpace, s.arg2intvar(call->arg(0)), irt, s.arg2intvar(call->arg(1)), 94 Reify(s.arg2boolvar(call->arg(2)), rm), GecodeSolverInstance::ann2icl(ann)); 95 } else { 96 rel(*s.currentSpace, s.arg2intvar(call->arg(0)), irt, 97 static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()), 98 Reify(s.arg2boolvar(call->arg(2)), rm), GecodeSolverInstance::ann2icl(ann)); 99 } 100 } else { 101 rel(*s.currentSpace, s.arg2intvar(call->arg(1)), swap(irt), 102 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()), 103 Reify(s.arg2boolvar(call->arg(2)), rm), GecodeSolverInstance::ann2icl(ann)); 104 } 105} 106 107///* Comparisons */ 108void p_int_eq_reif(SolverInstanceBase& s, const Call* call) { 109 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_EQV, call); 110} 111void p_int_ne_reif(SolverInstanceBase& s, const Call* call) { 112 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_EQV, call); 113} 114void p_int_ge_reif(SolverInstanceBase& s, const Call* call) { 115 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_EQV, call); 116} 117void p_int_gt_reif(SolverInstanceBase& s, const Call* call) { 118 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_EQV, call); 119} 120void p_int_le_reif(SolverInstanceBase& s, const Call* call) { 121 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_EQV, call); 122} 123void p_int_lt_reif(SolverInstanceBase& s, const Call* call) { 124 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_EQV, call); 125} 126 127void p_int_eq_imp(SolverInstanceBase& s, const Call* call) { 128 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_IMP, call); 129} 130void p_int_ne_imp(SolverInstanceBase& s, const Call* call) { 131 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_IMP, call); 132} 133void p_int_ge_imp(SolverInstanceBase& s, const Call* call) { 134 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_IMP, call); 135} 136void p_int_gt_imp(SolverInstanceBase& s, const Call* call) { 137 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_IMP, call); 138} 139void p_int_le_imp(SolverInstanceBase& s, const Call* call) { 140 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_IMP, call); 141} 142void p_int_lt_imp(SolverInstanceBase& s, const Call* call) { 143 p_int_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_IMP, call); 144} 145 146void p_int_lin_cmp(GecodeSolverInstance& s, IntRelType irt, const Call* call) { 147 const Annotation& ann = call->ann(); 148 IntArgs ia = GecodeSolverInstance::arg2intargs(call->arg(0)); 149 ArrayLit* vars = s.arg2arraylit(call->arg(1)); 150 int singleIntVar; 151 if (s.isBoolArray(vars, singleIntVar)) { 152 if (singleIntVar != -1) { 153 if (std::abs(ia[singleIntVar]) == 1 && call->arg(2)->cast<IntLit>()->v().toInt() == 0) { 154 IntVar siv = s.arg2intvar((*vars)[singleIntVar]); 155 BoolVarArgs iv = s.arg2boolvarargs(vars, 0, singleIntVar); 156 IntArgs ia_tmp(ia.size() - 1); 157 int count = 0; 158 for (int i = 0; i < ia.size(); i++) { 159 if (i != singleIntVar) { 160 ia_tmp[count++] = ia[singleIntVar] == -1 ? ia[i] : -ia[i]; 161 } 162 } 163 IntRelType t = (ia[singleIntVar] == -1 ? irt : swap(irt)); 164 linear(*s.currentSpace, ia_tmp, iv, t, siv, GecodeSolverInstance::ann2icl(ann)); 165 } else { 166 IntVarArgs iv = s.arg2intvarargs(vars); 167 linear(*s.currentSpace, ia, iv, irt, 168 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 169 GecodeSolverInstance::ann2icl(ann)); 170 } 171 } else { 172 BoolVarArgs iv = s.arg2boolvarargs(vars); 173 linear(*s.currentSpace, ia, iv, irt, 174 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 175 GecodeSolverInstance::ann2icl(ann)); 176 } 177 } else { 178 IntVarArgs iv = s.arg2intvarargs(vars); 179 linear(*s.currentSpace, ia, iv, irt, 180 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 181 GecodeSolverInstance::ann2icl(ann)); 182 } 183} 184void p_int_lin_cmp_reif(GecodeSolverInstance& s, IntRelType irt, ReifyMode rm, const Call* call) { 185 const Annotation& ann = call->ann(); 186 if (rm == RM_EQV && call->arg(2)->type().isbool()) { 187 if (call->arg(2)->cast<BoolLit>()->v()) { 188 p_int_lin_cmp(s, irt, call); 189 } else { 190 p_int_lin_cmp(s, neg(irt), call); 191 } 192 return; 193 } 194 IntArgs ia = GecodeSolverInstance::arg2intargs(call->arg(0)); 195 ArrayLit* vars = s.arg2arraylit(call->arg(1)); 196 int singleIntVar; 197 if (s.isBoolArray(vars, singleIntVar)) { 198 if (singleIntVar != -1) { 199 if (std::abs(ia[singleIntVar]) == 1 && call->arg(2)->cast<IntLit>()->v().toInt() == 0) { 200 IntVar siv = s.arg2intvar((*vars)[singleIntVar]); 201 BoolVarArgs iv = s.arg2boolvarargs(vars, 0, singleIntVar); 202 IntArgs ia_tmp(ia.size() - 1); 203 int count = 0; 204 for (int i = 0; i < ia.size(); i++) { 205 if (i != singleIntVar) { 206 ia_tmp[count++] = ia[singleIntVar] == -1 ? ia[i] : -ia[i]; 207 } 208 } 209 IntRelType t = (ia[singleIntVar] == -1 ? irt : swap(irt)); 210 linear(*s.currentSpace, ia_tmp, iv, t, siv, Reify(s.arg2boolvar(call->arg(3)), rm), 211 GecodeSolverInstance::ann2icl(ann)); 212 } else { 213 IntVarArgs iv = s.arg2intvarargs(vars); 214 linear(*s.currentSpace, ia, iv, irt, 215 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 216 Reify(s.arg2boolvar(call->arg(3)), rm), GecodeSolverInstance::ann2icl(ann)); 217 } 218 } else { 219 BoolVarArgs iv = s.arg2boolvarargs(vars); 220 linear(*s.currentSpace, ia, iv, irt, 221 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 222 Reify(s.arg2boolvar(call->arg(3)), rm), GecodeSolverInstance::ann2icl(ann)); 223 } 224 } else { 225 IntVarArgs iv = s.arg2intvarargs(vars); 226 linear(*s.currentSpace, ia, iv, irt, 227 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 228 Reify(s.arg2boolvar(call->arg(3)), rm), GecodeSolverInstance::ann2icl(ann)); 229 } 230} 231 232void p_int_lin_eq(SolverInstanceBase& s, const Call* call) { 233 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_EQ, call); 234} 235void p_int_lin_eq_reif(SolverInstanceBase& s, const Call* call) { 236 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_EQV, call); 237} 238void p_int_lin_eq_imp(SolverInstanceBase& s, const Call* call) { 239 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_IMP, call); 240} 241void p_int_lin_ne(SolverInstanceBase& s, const Call* call) { 242 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_NQ, call); 243} 244void p_int_lin_ne_reif(SolverInstanceBase& s, const Call* call) { 245 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_EQV, call); 246} 247void p_int_lin_ne_imp(SolverInstanceBase& s, const Call* call) { 248 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_IMP, call); 249} 250void p_int_lin_le(SolverInstanceBase& s, const Call* call) { 251 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LQ, call); 252} 253void p_int_lin_le_reif(SolverInstanceBase& s, const Call* call) { 254 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_EQV, call); 255} 256void p_int_lin_le_imp(SolverInstanceBase& s, const Call* call) { 257 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_IMP, call); 258} 259void p_int_lin_lt(SolverInstanceBase& s, const Call* call) { 260 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LE, call); 261} 262void p_int_lin_lt_reif(SolverInstanceBase& s, const Call* call) { 263 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_EQV, call); 264} 265void p_int_lin_lt_imp(SolverInstanceBase& s, const Call* call) { 266 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_IMP, call); 267} 268void p_int_lin_ge(SolverInstanceBase& s, const Call* call) { 269 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GQ, call); 270} 271void p_int_lin_ge_reif(SolverInstanceBase& s, const Call* call) { 272 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_EQV, call); 273} 274void p_int_lin_ge_imp(SolverInstanceBase& s, const Call* call) { 275 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_IMP, call); 276} 277void p_int_lin_gt(SolverInstanceBase& s, const Call* call) { 278 p_int_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GR, call); 279} 280void p_int_lin_gt_reif(SolverInstanceBase& s, const Call* call) { 281 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_EQV, call); 282} 283void p_int_lin_gt_imp(SolverInstanceBase& s, const Call* call) { 284 p_int_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_IMP, call); 285} 286 287void p_bool_lin_cmp(GecodeSolverInstance& s, IntRelType irt, const Call* call) { 288 const Annotation& ann = call->ann(); 289 IntArgs ia = GecodeSolverInstance::arg2intargs(call->arg(0)); 290 BoolVarArgs iv = s.arg2boolvarargs(call->arg(1)); 291 if (call->arg(2)->type().isvarint()) { 292 linear(*s.currentSpace, ia, iv, irt, 293 s.resolveVar(call->arg(2)->cast<Id>()->decl()).intVar(s.currentSpace), 294 GecodeSolverInstance::ann2icl(ann)); 295 } else { 296 linear(*s.currentSpace, ia, iv, irt, 297 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 298 GecodeSolverInstance::ann2icl(ann)); 299 } 300} 301void p_bool_lin_cmp_reif(GecodeSolverInstance& s, IntRelType irt, ReifyMode rm, const Call* call) { 302 const Annotation& ann = call->ann(); 303 if (rm == RM_EQV && call->arg(2)->type().isbool()) { 304 if (call->arg(2)->cast<BoolLit>()->v()) { 305 p_bool_lin_cmp(s, irt, call); 306 } else { 307 p_bool_lin_cmp(s, neg(irt), call); 308 } 309 return; 310 } 311 IntArgs ia = GecodeSolverInstance::arg2intargs(call->arg(0)); 312 BoolVarArgs iv = s.arg2boolvarargs(call->arg(1)); 313 if (call->arg(2)->type().isvarint()) { 314 linear(*s.currentSpace, ia, iv, irt, 315 s.resolveVar(call->arg(2)->cast<Id>()->decl()).intVar(s.currentSpace), 316 Reify(s.arg2boolvar(call->arg(3)), rm), GecodeSolverInstance::ann2icl(ann)); 317 } else { 318 linear(*s.currentSpace, ia, iv, irt, 319 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 320 Reify(s.arg2boolvar(call->arg(3)), rm), GecodeSolverInstance::ann2icl(ann)); 321 } 322} 323void p_bool_lin_eq(SolverInstanceBase& s, const Call* call) { 324 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_EQ, call); 325} 326void p_bool_lin_eq_reif(SolverInstanceBase& s, const Call* call) { 327 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_EQV, call); 328} 329void p_bool_lin_eq_imp(SolverInstanceBase& s, const Call* call) { 330 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_IMP, call); 331} 332void p_bool_lin_ne(SolverInstanceBase& s, const Call* call) { 333 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_NQ, call); 334} 335void p_bool_lin_ne_reif(SolverInstanceBase& s, const Call* call) { 336 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_EQV, call); 337} 338void p_bool_lin_ne_imp(SolverInstanceBase& s, const Call* call) { 339 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_IMP, call); 340} 341void p_bool_lin_le(SolverInstanceBase& s, const Call* call) { 342 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LQ, call); 343} 344void p_bool_lin_le_reif(SolverInstanceBase& s, const Call* call) { 345 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_EQV, call); 346} 347void p_bool_lin_le_imp(SolverInstanceBase& s, const Call* call) { 348 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_IMP, call); 349} 350void p_bool_lin_lt(SolverInstanceBase& s, const Call* call) { 351 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LE, call); 352} 353void p_bool_lin_lt_reif(SolverInstanceBase& s, const Call* call) { 354 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_EQV, call); 355} 356void p_bool_lin_lt_imp(SolverInstanceBase& s, const Call* call) { 357 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_IMP, call); 358} 359void p_bool_lin_ge(SolverInstanceBase& s, const Call* call) { 360 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GQ, call); 361} 362void p_bool_lin_ge_reif(SolverInstanceBase& s, const Call* call) { 363 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_EQV, call); 364} 365void p_bool_lin_ge_imp(SolverInstanceBase& s, const Call* call) { 366 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_IMP, call); 367} 368void p_bool_lin_gt(SolverInstanceBase& s, const Call* call) { 369 p_bool_lin_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GR, call); 370} 371void p_bool_lin_gt_reif(SolverInstanceBase& s, const Call* call) { 372 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_EQV, call); 373} 374void p_bool_lin_gt_imp(SolverInstanceBase& s, const Call* call) { 375 p_bool_lin_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_IMP, call); 376} 377 378///* arithmetic constraints */ 379 380void p_int_plus(SolverInstanceBase& s, const Call* call) { 381 auto& gi = static_cast<GecodeSolverInstance&>(s); 382 if (!call->arg(0)->type().isvarint()) { 383 rel(*gi.currentSpace, 384 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()) + gi.arg2intvar(call->arg(1)) == 385 gi.arg2intvar(call->arg(2)), 386 GecodeSolverInstance::ann2icl(call->ann())); 387 } else if (!call->arg(1)->type().isvarint()) { 388 rel(*gi.currentSpace, 389 gi.arg2intvar(call->arg(0)) + static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()) == 390 gi.arg2intvar(call->arg(2)), 391 GecodeSolverInstance::ann2icl(call->ann())); 392 } else if (!call->arg(2)->type().isvarint()) { 393 rel(*gi.currentSpace, 394 gi.arg2intvar(call->arg(0)) + gi.arg2intvar(call->arg(1)) == 395 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 396 GecodeSolverInstance::ann2icl(call->ann())); 397 } else { 398 rel(*gi.currentSpace, 399 gi.arg2intvar(call->arg(0)) + gi.arg2intvar(call->arg(1)) == gi.arg2intvar(call->arg(2)), 400 GecodeSolverInstance::ann2icl(call->ann())); 401 } 402} 403 404void p_int_minus(SolverInstanceBase& s, const Call* call) { 405 auto& gi = static_cast<GecodeSolverInstance&>(s); 406 if (!call->arg(0)->type().isvarint()) { 407 rel(*gi.currentSpace, 408 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()) - gi.arg2intvar(call->arg(1)) == 409 gi.arg2intvar(call->arg(2)), 410 GecodeSolverInstance::ann2icl(call->ann())); 411 } else if (!call->arg(1)->type().isvarint()) { 412 rel(*gi.currentSpace, 413 gi.arg2intvar(call->arg(0)) - static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()) == 414 gi.arg2intvar(call->arg(2)), 415 GecodeSolverInstance::ann2icl(call->ann())); 416 } else if (!call->arg(2)->type().isvarint()) { 417 rel(*gi.currentSpace, 418 gi.arg2intvar(call->arg(0)) - gi.arg2intvar(call->arg(1)) == 419 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 420 GecodeSolverInstance::ann2icl(call->ann())); 421 } else { 422 rel(*gi.currentSpace, 423 gi.arg2intvar(call->arg(0)) - gi.arg2intvar(call->arg(1)) == gi.arg2intvar(call->arg(2)), 424 GecodeSolverInstance::ann2icl(call->ann())); 425 } 426} 427 428void p_int_times(SolverInstanceBase& s, const Call* call) { 429 auto& gi = static_cast<GecodeSolverInstance&>(s); 430 IntVar x0 = gi.arg2intvar(call->arg(0)); 431 IntVar x1 = gi.arg2intvar(call->arg(1)); 432 IntVar x2 = gi.arg2intvar(call->arg(2)); 433 mult(*gi.currentSpace, x0, x1, x2, GecodeSolverInstance::ann2icl(call->ann())); 434} 435void p_int_div(SolverInstanceBase& s, const Call* call) { 436 auto& gi = static_cast<GecodeSolverInstance&>(s); 437 IntVar x0 = gi.arg2intvar(call->arg(0)); 438 IntVar x1 = gi.arg2intvar(call->arg(1)); 439 IntVar x2 = gi.arg2intvar(call->arg(2)); 440 div(*gi.currentSpace, x0, x1, x2, GecodeSolverInstance::ann2icl(call->ann())); 441} 442void p_int_mod(SolverInstanceBase& s, const Call* call) { 443 auto& gi = static_cast<GecodeSolverInstance&>(s); 444 IntVar x0 = gi.arg2intvar(call->arg(0)); 445 IntVar x1 = gi.arg2intvar(call->arg(1)); 446 IntVar x2 = gi.arg2intvar(call->arg(2)); 447 mod(*gi.currentSpace, x0, x1, x2, GecodeSolverInstance::ann2icl(call->ann())); 448} 449 450void p_int_min(SolverInstanceBase& s, const Call* call) { 451 auto& gi = static_cast<GecodeSolverInstance&>(s); 452 IntVar x0 = gi.arg2intvar(call->arg(0)); 453 IntVar x1 = gi.arg2intvar(call->arg(1)); 454 IntVar x2 = gi.arg2intvar(call->arg(2)); 455 min(*gi.currentSpace, x0, x1, x2, GecodeSolverInstance::ann2icl(call->ann())); 456} 457void p_int_max(SolverInstanceBase& s, const Call* call) { 458 auto& gi = static_cast<GecodeSolverInstance&>(s); 459 IntVar x0 = gi.arg2intvar(call->arg(0)); 460 IntVar x1 = gi.arg2intvar(call->arg(1)); 461 IntVar x2 = gi.arg2intvar(call->arg(2)); 462 max(*gi.currentSpace, x0, x1, x2, GecodeSolverInstance::ann2icl(call->ann())); 463} 464void p_int_negate(SolverInstanceBase& s, const Call* call) { 465 auto& gi = static_cast<GecodeSolverInstance&>(s); 466 IntVar x0 = gi.arg2intvar(call->arg(0)); 467 IntVar x1 = gi.arg2intvar(call->arg(1)); 468 rel(*gi.currentSpace, x0 == -x1, GecodeSolverInstance::ann2icl(call->ann())); 469} 470 471///* Boolean constraints */ 472void p_bool_cmp(GecodeSolverInstance& s, IntRelType irt, const Call* call) { 473 const Annotation& ann = call->ann(); 474 rel(*s.currentSpace, s.arg2boolvar(call->arg(0)), irt, s.arg2boolvar(call->arg(1)), 475 GecodeSolverInstance::ann2icl(ann)); 476} 477void p_bool_cmp_reif(GecodeSolverInstance& s, IntRelType irt, ReifyMode rm, const Call* call) { 478 const Annotation& ann = call->ann(); 479 rel(*s.currentSpace, s.arg2boolvar(call->arg(0)), irt, s.arg2boolvar(call->arg(1)), 480 Reify(s.arg2boolvar(call->arg(2)), rm), GecodeSolverInstance::ann2icl(ann)); 481} 482void p_bool_eq(SolverInstanceBase& s, const Call* call) { 483 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_EQ, call); 484} 485void p_bool_eq_reif(SolverInstanceBase& s, const Call* call) { 486 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_EQV, call); 487} 488void p_bool_eq_imp(SolverInstanceBase& s, const Call* call) { 489 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_EQ, RM_IMP, call); 490} 491void p_bool_ne(SolverInstanceBase& s, const Call* call) { 492 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_NQ, call); 493} 494void p_bool_ne_reif(SolverInstanceBase& s, const Call* call) { 495 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_EQV, call); 496} 497void p_bool_ne_imp(SolverInstanceBase& s, const Call* call) { 498 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_NQ, RM_IMP, call); 499} 500void p_bool_ge(SolverInstanceBase& s, const Call* call) { 501 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GQ, call); 502} 503void p_bool_ge_reif(SolverInstanceBase& s, const Call* call) { 504 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_EQV, call); 505} 506void p_bool_ge_imp(SolverInstanceBase& s, const Call* call) { 507 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GQ, RM_IMP, call); 508} 509void p_bool_le(SolverInstanceBase& s, const Call* call) { 510 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LQ, call); 511} 512void p_bool_le_reif(SolverInstanceBase& s, const Call* call) { 513 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_EQV, call); 514} 515void p_bool_le_imp(SolverInstanceBase& s, const Call* call) { 516 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LQ, RM_IMP, call); 517} 518void p_bool_gt(SolverInstanceBase& s, const Call* call) { 519 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_GR, call); 520} 521void p_bool_gt_reif(SolverInstanceBase& s, const Call* call) { 522 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_EQV, call); 523} 524void p_bool_gt_imp(SolverInstanceBase& s, const Call* call) { 525 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_GR, RM_IMP, call); 526} 527void p_bool_lt(SolverInstanceBase& s, const Call* call) { 528 p_bool_cmp(static_cast<GecodeSolverInstance&>(s), IRT_LE, call); 529} 530void p_bool_lt_reif(SolverInstanceBase& s, const Call* call) { 531 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_EQV, call); 532} 533void p_bool_lt_imp(SolverInstanceBase& s, const Call* call) { 534 p_bool_cmp_reif(static_cast<GecodeSolverInstance&>(s), IRT_LE, RM_IMP, call); 535} 536 537#define BOOL_OP(op) \ 538 BoolVar b0 = gi.arg2boolvar(call->arg(0)); \ 539 BoolVar b1 = gi.arg2boolvar(call->arg(1)); \ 540 if (!call->arg(2)->type().isvar() && call->arg(2)->type().isbool()) { \ 541 rel(*gi.currentSpace, b0, op, b1, call->arg(2)->cast<BoolLit>()->v(), gi.ann2icl(ann)); \ 542 } else { \ 543 rel(*gi.currentSpace, b0, op, b1, \ 544 gi.resolveVar(gi.getVarDecl(call->arg(2))).boolVar(gi.currentSpace), gi.ann2icl(ann)); \ 545 } 546 547#define BOOL_ARRAY_OP(op) \ 548 BoolVarArgs bv = gi.arg2boolvarargs(call->arg(0)); \ 549 if (call->argCount() == 1) { \ 550 rel(*gi.currentSpace, op, bv, 1, gi.ann2icl(ann)); \ 551 } else if (!call->arg(1)->type().isvar() && call->arg(1)->type().isbool()) { \ 552 rel(*gi.currentSpace, op, bv, call->arg(1)->cast<BoolLit>()->v(), gi.ann2icl(ann)); \ 553 } else { \ 554 rel(*gi.currentSpace, op, bv, \ 555 gi.resolveVar(gi.getVarDecl(call->arg(1))).boolVar(gi.currentSpace), gi.ann2icl(ann)); \ 556 } 557 558void p_bool_or(SolverInstanceBase& s, const Call* call) { 559 const Annotation& ann = call->ann(); 560 auto& gi = static_cast<GecodeSolverInstance&>(s); 561 BOOL_OP(BoolOpType::BOT_OR); 562} 563void p_bool_or_imp(SolverInstanceBase& s, const Call* call) { 564 const Annotation& ann = call->ann(); 565 auto& gi = static_cast<GecodeSolverInstance&>(s); 566 BoolVar b0 = gi.arg2boolvar(call->arg(0)); 567 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 568 BoolVar b2 = gi.arg2boolvar(call->arg(2)); 569 clause(*gi.currentSpace, BoolOpType::BOT_OR, BoolVarArgs() << b0 << b1, BoolVarArgs() << b2, 1, 570 GecodeSolverInstance::ann2icl(ann)); 571} 572void p_bool_and(SolverInstanceBase& s, const Call* call) { 573 const Annotation& ann = call->ann(); 574 auto& gi = static_cast<GecodeSolverInstance&>(s); 575 BOOL_OP(BoolOpType::BOT_AND); 576} 577void p_bool_and_imp(SolverInstanceBase& s, const Call* call) { 578 const Annotation& ann = call->ann(); 579 auto& gi = static_cast<GecodeSolverInstance&>(s); 580 BoolVar b0 = gi.arg2boolvar(call->arg(0)); 581 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 582 BoolVar b2 = gi.arg2boolvar(call->arg(2)); 583 rel(*gi.currentSpace, b2, BoolOpType::BOT_IMP, b0, 1, GecodeSolverInstance::ann2icl(ann)); 584 rel(*gi.currentSpace, b2, BoolOpType::BOT_IMP, b1, 1, GecodeSolverInstance::ann2icl(ann)); 585} 586void p_array_bool_and(SolverInstanceBase& s, const Call* call) { 587 const Annotation& ann = call->ann(); 588 auto& gi = static_cast<GecodeSolverInstance&>(s); 589 BOOL_ARRAY_OP(Gecode::BoolOpType::BOT_AND); 590} 591void p_array_bool_and_imp(SolverInstanceBase& s, const Call* call) { 592 const Annotation& ann = call->ann(); 593 auto& gi = static_cast<GecodeSolverInstance&>(s); 594 BoolVarArgs bv = gi.arg2boolvarargs(call->arg(0)); 595 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 596 for (int i = static_cast<int>(bv.size()); (i--) != 0;) { 597 rel(*gi.currentSpace, b1, Gecode::BoolOpType::BOT_IMP, bv[i], 1, 598 GecodeSolverInstance::ann2icl(ann)); 599 } 600} 601void p_array_bool_or(SolverInstanceBase& s, const Call* call) { 602 const Annotation& ann = call->ann(); 603 auto& gi = static_cast<GecodeSolverInstance&>(s); 604 BOOL_ARRAY_OP(BoolOpType::BOT_OR); 605} 606void p_array_bool_or_imp(SolverInstanceBase& s, const Call* call) { 607 const Annotation& ann = call->ann(); 608 auto& gi = static_cast<GecodeSolverInstance&>(s); 609 BoolVarArgs bv = gi.arg2boolvarargs(call->arg(0)); 610 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 611 clause(*gi.currentSpace, BoolOpType::BOT_OR, bv, BoolVarArgs() << b1, 1, 612 GecodeSolverInstance::ann2icl(ann)); 613} 614void p_array_bool_xor(SolverInstanceBase& s, const Call* call) { 615 const Annotation& ann = call->ann(); 616 auto& gi = static_cast<GecodeSolverInstance&>(s); 617 BOOL_ARRAY_OP(BoolOpType::BOT_XOR); 618} 619void p_array_bool_xor_imp(SolverInstanceBase& s, const Call* call) { 620 const Annotation& ann = call->ann(); 621 auto& gi = static_cast<GecodeSolverInstance&>(s); 622 BoolVarArgs bv = gi.arg2boolvarargs(call->arg(0)); 623 BoolVar tmp(*gi.currentSpace, 0, 1); 624 rel(*gi.currentSpace, BoolOpType::BOT_XOR, bv, tmp, GecodeSolverInstance::ann2icl(ann)); 625 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(1)), BoolOpType::BOT_IMP, tmp, 1); 626} 627void p_array_bool_clause(SolverInstanceBase& s, const Call* call) { 628 const Annotation& ann = call->ann(); 629 auto& gi = static_cast<GecodeSolverInstance&>(s); 630 BoolVarArgs bvp = gi.arg2boolvarargs(call->arg(0)); 631 BoolVarArgs bvn = gi.arg2boolvarargs(call->arg(1)); 632 clause(*gi.currentSpace, BoolOpType::BOT_OR, bvp, bvn, 1, GecodeSolverInstance::ann2icl(ann)); 633} 634void p_array_bool_clause_reif(SolverInstanceBase& s, const Call* call) { 635 const Annotation& ann = call->ann(); 636 auto& gi = static_cast<GecodeSolverInstance&>(s); 637 BoolVarArgs bvp = gi.arg2boolvarargs(call->arg(0)); 638 BoolVarArgs bvn = gi.arg2boolvarargs(call->arg(1)); 639 BoolVar b0 = gi.arg2boolvar(call->arg(2)); 640 clause(*gi.currentSpace, BoolOpType::BOT_OR, bvp, bvn, b0, GecodeSolverInstance::ann2icl(ann)); 641} 642void p_array_bool_clause_imp(SolverInstanceBase& s, const Call* call) { 643 const Annotation& ann = call->ann(); 644 auto& gi = static_cast<GecodeSolverInstance&>(s); 645 BoolVarArgs bvp = gi.arg2boolvarargs(call->arg(0)); 646 BoolVarArgs bvn = gi.arg2boolvarargs(call->arg(1)); 647 BoolVar b0 = gi.arg2boolvar(call->arg(2)); 648 clause(*gi.currentSpace, BoolOpType::BOT_OR, bvp, bvn, b0, GecodeSolverInstance::ann2icl(ann)); 649} 650void p_bool_xor(SolverInstanceBase& s, const Call* call) { 651 const Annotation& ann = call->ann(); 652 auto& gi = static_cast<GecodeSolverInstance&>(s); 653 BOOL_OP(BoolOpType::BOT_XOR); 654} 655void p_bool_xor_imp(SolverInstanceBase& s, const Call* call) { 656 const Annotation& ann = call->ann(); 657 auto& gi = static_cast<GecodeSolverInstance&>(s); 658 BoolVar b0 = gi.arg2boolvar(call->arg(0)); 659 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 660 BoolVar b2 = gi.arg2boolvar(call->arg(2)); 661 clause(*gi.currentSpace, BoolOpType::BOT_OR, BoolVarArgs() << b0 << b1, BoolVarArgs() << b2, 1, 662 GecodeSolverInstance::ann2icl(ann)); 663 clause(*gi.currentSpace, BoolOpType::BOT_OR, BoolVarArgs(), BoolVarArgs() << b0 << b1 << b2, 1, 664 GecodeSolverInstance::ann2icl(ann)); 665} 666void p_bool_l_imp(SolverInstanceBase& s, const Call* call) { 667 const Annotation& ann = call->ann(); 668 auto& gi = static_cast<GecodeSolverInstance&>(s); 669 BoolVar b0 = gi.arg2boolvar(call->arg(0)); 670 BoolVar b1 = gi.arg2boolvar(call->arg(1)); 671 if (call->arg(2)->type().isbool()) { 672 rel(*gi.currentSpace, b1, BoolOpType::BOT_IMP, b0, 673 static_cast<int>(call->arg(2)->cast<BoolLit>()->v()), GecodeSolverInstance::ann2icl(ann)); 674 } else { 675 rel(*gi.currentSpace, b1, BoolOpType::BOT_IMP, b0, 676 gi.resolveVar(call->arg(2)->cast<Id>()->decl()).boolVar(gi.currentSpace), 677 GecodeSolverInstance::ann2icl(ann)); 678 } 679} 680void p_bool_r_imp(SolverInstanceBase& s, const Call* call) { 681 const Annotation& ann = call->ann(); 682 auto& gi = static_cast<GecodeSolverInstance&>(s); 683 BOOL_OP(BoolOpType::BOT_IMP); 684} 685void p_bool_not(SolverInstanceBase& s, const Call* call) { 686 const Annotation& ann = call->ann(); 687 auto& gi = static_cast<GecodeSolverInstance&>(s); 688 BoolVar x0 = gi.arg2boolvar(call->arg(0)); 689 BoolVar x1 = gi.arg2boolvar(call->arg(1)); 690 rel(*gi.currentSpace, x0, BoolOpType::BOT_XOR, x1, 1, GecodeSolverInstance::ann2icl(ann)); 691} 692 693///* element constraints */ 694void p_array_int_element(SolverInstanceBase& s, const Call* call) { 695 const Annotation& ann = call->ann(); 696 auto& gi = static_cast<GecodeSolverInstance&>(s); 697 IntVar selector = gi.arg2intvar(call->arg(0)); 698 rel(*gi.currentSpace, selector > 0); 699 if (call->arg(1)->type().isvar()) { 700 IntVarArgs iv = gi.arg2intvarargs(call->arg(1), 1); 701 element(*gi.currentSpace, iv, selector, gi.arg2intvar(call->arg(2)), 702 GecodeSolverInstance::ann2icl(ann)); 703 } else { 704 IntArgs ia = GecodeSolverInstance::arg2intargs(call->arg(1), 1); 705 element(*gi.currentSpace, ia, selector, gi.arg2intvar(call->arg(2)), 706 GecodeSolverInstance::ann2icl(ann)); 707 } 708} 709void p_array_bool_element(SolverInstanceBase& s, const Call* call) { 710 const Annotation& ann = call->ann(); 711 auto& gi = static_cast<GecodeSolverInstance&>(s); 712 IntVar selector = gi.arg2intvar(call->arg(0)); 713 rel(*gi.currentSpace, selector > 0); 714 if (call->arg(1)->type().isvar()) { 715 BoolVarArgs iv = gi.arg2boolvarargs(call->arg(1), 1); 716 element(*gi.currentSpace, iv, selector, gi.arg2boolvar(call->arg(2)), 717 GecodeSolverInstance::ann2icl(ann)); 718 } else { 719 IntArgs ia = GecodeSolverInstance::arg2boolargs(call->arg(1), 1); 720 element(*gi.currentSpace, ia, selector, gi.arg2boolvar(call->arg(2)), 721 GecodeSolverInstance::ann2icl(ann)); 722 } 723} 724 725///* coercion constraints */ 726void p_bool2int(SolverInstanceBase& s, const Call* call) { 727 const Annotation& ann = call->ann(); 728 auto& gi = static_cast<GecodeSolverInstance&>(s); 729 BoolVar x0 = gi.arg2boolvar(call->arg(0)); 730 IntVar x1 = gi.arg2intvar(call->arg(1)); 731 if (call->arg(0)->type().isvarbool() && call->arg(1)->type().isvarint()) { 732 unsigned int index = gi.resolveVar(call->arg(0)->cast<Id>()->decl()).index(); 733 gi.resolveVar(call->arg(1)->cast<Id>()->decl()).setBoolAliasIndex(index); 734 } 735 channel(*gi.currentSpace, x0, x1, GecodeSolverInstance::ann2icl(ann)); 736} 737 738void p_int_in(SolverInstanceBase& s, const Call* call) { 739 auto& gi = static_cast<GecodeSolverInstance&>(s); 740 IntSet d = gi.arg2intset(s.env().envi(), call->arg(1)); 741 if (call->arg(0)->type().isvarbool()) { 742 Gecode::IntSetRanges dr(d); 743 Iter::Ranges::Singleton sr(0, 1); 744 Iter::Ranges::Inter<Gecode::IntSetRanges, Iter::Ranges::Singleton> i(dr, sr); 745 IntSet d01(i); 746 if (d01.size() == 0) { 747 gi.currentSpace->fail(); 748 } else { 749 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(0)), IRT_GQ, d01.min()); 750 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(0)), IRT_LQ, d01.max()); 751 } 752 } else { 753 dom(*gi.currentSpace, gi.arg2intvar(call->arg(0)), d); 754 } 755} 756void p_int_in_reif(SolverInstanceBase& s, const Call* call) { 757 auto& gi = static_cast<GecodeSolverInstance&>(s); 758 IntSet d = gi.arg2intset(s.env().envi(), call->arg(1)); 759 if (call->arg(0)->type().isvarbool()) { 760 Gecode::IntSetRanges dr(d); 761 Iter::Ranges::Singleton sr(0, 1); 762 Iter::Ranges::Inter<Gecode::IntSetRanges, Iter::Ranges::Singleton> i(dr, sr); 763 IntSet d01(i); 764 if (d01.size() == 0) { 765 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) == 0); 766 } else if (d01.max() == 0) { 767 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) == !gi.arg2boolvar(call->arg(0))); 768 } else if (d01.min() == 1) { 769 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) == gi.arg2boolvar(call->arg(0))); 770 } else { 771 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) == 1); 772 } 773 } else { 774 dom(*gi.currentSpace, gi.arg2intvar(call->arg(0)), d, gi.arg2boolvar(call->arg(2))); 775 } 776} 777void p_int_in_imp(SolverInstanceBase& s, const Call* call) { 778 auto& gi = static_cast<GecodeSolverInstance&>(s); 779 IntSet d = gi.arg2intset(s.env().envi(), call->arg(1)); 780 if (call->arg(0)->type().isvarbool()) { 781 Gecode::IntSetRanges dr(d); 782 Iter::Ranges::Singleton sr(0, 1); 783 Iter::Ranges::Inter<Gecode::IntSetRanges, Iter::Ranges::Singleton> i(dr, sr); 784 IntSet d01(i); 785 if (d01.size() == 0) { 786 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) == 0); 787 } else if (d01.max() == 0) { 788 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) >> !gi.arg2boolvar(call->arg(0))); 789 } else if (d01.min() == 1) { 790 rel(*gi.currentSpace, gi.arg2boolvar(call->arg(2)) >> gi.arg2boolvar(call->arg(0))); 791 } 792 } else { 793 dom(*gi.currentSpace, gi.arg2intvar(call->arg(0)), d, 794 Reify(gi.arg2boolvar(call->arg(2)), RM_IMP)); 795 } 796} 797 798///* constraints from the standard library */ 799 800void p_abs(SolverInstanceBase& s, const Call* call) { 801 const Annotation& ann = call->ann(); 802 auto& gi = static_cast<GecodeSolverInstance&>(s); 803 IntVar x0 = gi.arg2intvar(call->arg(0)); 804 IntVar x1 = gi.arg2intvar(call->arg(1)); 805 abs(*gi.currentSpace, x0, x1, GecodeSolverInstance::ann2icl(ann)); 806} 807 808void p_array_int_lt(SolverInstanceBase& s, const Call* call) { 809 const Annotation& ann = call->ann(); 810 auto& gi = static_cast<GecodeSolverInstance&>(s); 811 IntVarArgs iv0 = gi.arg2intvarargs(call->arg(0)); 812 IntVarArgs iv1 = gi.arg2intvarargs(call->arg(1)); 813 rel(*gi.currentSpace, iv0, IRT_LE, iv1, GecodeSolverInstance::ann2icl(ann)); 814} 815 816void p_array_int_lq(SolverInstanceBase& s, const Call* call) { 817 const Annotation& ann = call->ann(); 818 auto& gi = static_cast<GecodeSolverInstance&>(s); 819 IntVarArgs iv0 = gi.arg2intvarargs(call->arg(0)); 820 IntVarArgs iv1 = gi.arg2intvarargs(call->arg(1)); 821 rel(*gi.currentSpace, iv0, IRT_LQ, iv1, GecodeSolverInstance::ann2icl(ann)); 822} 823 824void p_array_bool_lt(SolverInstanceBase& s, const Call* call) { 825 const Annotation& ann = call->ann(); 826 auto& gi = static_cast<GecodeSolverInstance&>(s); 827 BoolVarArgs bv0 = gi.arg2boolvarargs(call->arg(0)); 828 BoolVarArgs bv1 = gi.arg2boolvarargs(call->arg(1)); 829 rel(*gi.currentSpace, bv0, IRT_LE, bv1, GecodeSolverInstance::ann2icl(ann)); 830} 831 832void p_array_bool_lq(SolverInstanceBase& s, const Call* call) { 833 const Annotation& ann = call->ann(); 834 auto& gi = static_cast<GecodeSolverInstance&>(s); 835 BoolVarArgs bv0 = gi.arg2boolvarargs(call->arg(0)); 836 BoolVarArgs bv1 = gi.arg2boolvarargs(call->arg(1)); 837 rel(*gi.currentSpace, bv0, IRT_LQ, bv1, GecodeSolverInstance::ann2icl(ann)); 838} 839 840void p_count(SolverInstanceBase& s, const Call* call) { 841 const Annotation& ann = call->ann(); 842 auto& gi = static_cast<GecodeSolverInstance&>(s); 843 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 844 if (!call->arg(1)->type().isvarint()) { 845 if (!call->arg(2)->type().isvarint()) { 846 count(*gi.currentSpace, iv, static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()), 847 IRT_EQ, static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 848 GecodeSolverInstance::ann2icl(ann)); 849 } else { 850 count(*gi.currentSpace, iv, static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()), 851 IRT_EQ, gi.arg2intvar(call->arg(2)), GecodeSolverInstance::ann2icl(ann)); 852 } 853 } else if (!call->arg(2)->type().isvarint()) { 854 count(*gi.currentSpace, iv, gi.arg2intvar(call->arg(1)), IRT_EQ, 855 static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), 856 GecodeSolverInstance::ann2icl(ann)); 857 } else { 858 count(*gi.currentSpace, iv, gi.arg2intvar(call->arg(1)), IRT_EQ, gi.arg2intvar(call->arg(2)), 859 GecodeSolverInstance::ann2icl(ann)); 860 } 861} 862 863void p_count_reif(SolverInstanceBase& s, const Call* call) { 864 const Annotation& ann = call->ann(); 865 auto& gi = static_cast<GecodeSolverInstance&>(s); 866 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 867 IntVar x = gi.arg2intvar(call->arg(1)); 868 IntVar y = gi.arg2intvar(call->arg(2)); 869 BoolVar b = gi.arg2boolvar(call->arg(3)); 870 IntVar c(*gi.currentSpace, 0, Int::Limits::max); 871 count(*gi.currentSpace, iv, x, IRT_EQ, c, GecodeSolverInstance::ann2icl(ann)); 872 rel(*gi.currentSpace, b == (c == y)); 873} 874void p_count_imp(SolverInstanceBase& s, const Call* call) { 875 const Annotation& ann = call->ann(); 876 auto& gi = static_cast<GecodeSolverInstance&>(s); 877 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 878 IntVar x = gi.arg2intvar(call->arg(1)); 879 IntVar y = gi.arg2intvar(call->arg(2)); 880 BoolVar b = gi.arg2boolvar(call->arg(3)); 881 IntVar c(*gi.currentSpace, 0, Int::Limits::max); 882 count(*gi.currentSpace, iv, x, IRT_EQ, c, GecodeSolverInstance::ann2icl(ann)); 883 rel(*gi.currentSpace, b >> (c == y)); 884} 885 886void count_rel(IntRelType irt, SolverInstanceBase& s, const Call* call) { 887 const Annotation& ann = call->ann(); 888 auto& gi = static_cast<GecodeSolverInstance&>(s); 889 IntVarArgs iv = gi.arg2intvarargs(call->arg(1)); 890 count(*gi.currentSpace, iv, static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()), irt, 891 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()), 892 GecodeSolverInstance::ann2icl(ann)); 893} 894 895void p_at_most(SolverInstanceBase& s, const Call* call) { count_rel(IRT_LQ, s, call); } 896 897void p_at_least(SolverInstanceBase& s, const Call* call) { count_rel(IRT_GQ, s, call); } 898 899void p_bin_packing_load(SolverInstanceBase& s, const Call* call) { 900 const Annotation& ann = call->ann(); 901 auto& gi = static_cast<GecodeSolverInstance&>(s); 902 int minIdx = static_cast<int>(call->arg(3)->cast<IntLit>()->v().toInt()); 903 IntVarArgs load = gi.arg2intvarargs(call->arg(0)); 904 IntVarArgs l; 905 IntVarArgs bin = gi.arg2intvarargs(call->arg(1)); 906 for (int i = bin.size(); (i--) != 0;) { 907 rel(*gi.currentSpace, bin[i] >= minIdx); 908 } 909 if (minIdx > 0) { 910 for (int i = minIdx; (i--) != 0;) { 911 l << IntVar(*gi.currentSpace, 0, 0); 912 } 913 } else if (minIdx < 0) { 914 IntVarArgs bin2(bin.size()); 915 for (int i = bin.size(); (i--) != 0;) { 916 bin2[i] = expr(*gi.currentSpace, bin[i] - minIdx, GecodeSolverInstance::ann2icl(ann)); 917 } 918 bin = bin2; 919 } 920 l << load; 921 IntArgs sizes = GecodeSolverInstance::arg2intargs(call->arg(2)); 922 923 IntVarArgs allvars = l + bin; 924 unshare(*gi.currentSpace, allvars); 925 binpacking(*gi.currentSpace, allvars.slice(0, 1, l.size()), 926 allvars.slice(l.size(), 1, bin.size()), sizes, GecodeSolverInstance::ann2icl(ann)); 927} 928 929void p_global_cardinality(SolverInstanceBase& s, const Call* call) { 930 const Annotation& ann = call->ann(); 931 auto& gi = static_cast<GecodeSolverInstance&>(s); 932 IntVarArgs iv0 = gi.arg2intvarargs(call->arg(0)); 933 IntArgs cover = GecodeSolverInstance::arg2intargs(call->arg(1)); 934 IntVarArgs iv1 = gi.arg2intvarargs(call->arg(2)); 935 936 Region re; 937 IntSet cover_s(cover); 938 Gecode::IntSetRanges cover_r(cover_s); 939 auto* iv0_ri = re.alloc<Gecode::IntVarRanges>(iv0.size()); 940 for (int i = iv0.size(); (i--) != 0;) { 941 iv0_ri[i] = Gecode::IntVarRanges(iv0[i]); 942 } 943 Iter::Ranges::NaryUnion iv0_r(re, iv0_ri, iv0.size()); 944 Iter::Ranges::Diff<Iter::Ranges::NaryUnion, Gecode::IntSetRanges> extra_r(iv0_r, cover_r); 945 Iter::Ranges::ToValues<Iter::Ranges::Diff<Iter::Ranges::NaryUnion, Gecode::IntSetRanges> > extra( 946 extra_r); 947 for (; extra(); ++extra) { 948 cover << extra.val(); 949 iv1 << IntVar(*gi.currentSpace, 0, iv0.size()); 950 } 951 952 MZ_IntConLevel icl = GecodeSolverInstance::ann2icl(ann); 953 if (icl == MZ_ICL_DOM) { 954 IntVarArgs allvars = iv0 + iv1; 955 unshare(*gi.currentSpace, allvars); 956 count(*gi.currentSpace, allvars.slice(0, 1, iv0.size()), 957 allvars.slice(iv0.size(), 1, iv1.size()), cover, GecodeSolverInstance::ann2icl(ann)); 958 } else { 959 unshare(*gi.currentSpace, iv0); 960 count(*gi.currentSpace, iv0, iv1, cover, GecodeSolverInstance::ann2icl(ann)); 961 } 962} 963 964void p_global_cardinality_closed(SolverInstanceBase& s, const Call* call) { 965 const Annotation& ann = call->ann(); 966 auto& gi = static_cast<GecodeSolverInstance&>(s); 967 IntVarArgs iv0 = gi.arg2intvarargs(call->arg(0)); 968 IntArgs cover = GecodeSolverInstance::arg2intargs(call->arg(1)); 969 IntVarArgs iv1 = gi.arg2intvarargs(call->arg(2)); 970 unshare(*gi.currentSpace, iv0); 971 count(*gi.currentSpace, iv0, iv1, cover, GecodeSolverInstance::ann2icl(ann)); 972} 973 974void p_global_cardinality_low_up(SolverInstanceBase& s, const Call* call) { 975 const Annotation& ann = call->ann(); 976 auto& gi = static_cast<GecodeSolverInstance&>(s); 977 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 978 IntArgs cover = GecodeSolverInstance::arg2intargs(call->arg(1)); 979 980 IntArgs lbound = GecodeSolverInstance::arg2intargs(call->arg(2)); 981 IntArgs ubound = GecodeSolverInstance::arg2intargs(call->arg(3)); 982 IntSetArgs y(cover.size()); 983 for (int i = cover.size(); (i--) != 0;) { 984 y[i] = IntSet(lbound[i], ubound[i]); 985 } 986 987 IntSet cover_s(cover); 988 Region re; 989 auto* xrs = re.alloc<IntVarRanges>(x.size()); 990 for (int i = x.size(); (i--) != 0;) { 991 xrs[i].init(x[i]); 992 } 993 Iter::Ranges::NaryUnion u(re, xrs, x.size()); 994 Iter::Ranges::ToValues<Iter::Ranges::NaryUnion> uv(u); 995 for (; uv(); ++uv) { 996 if (!cover_s.in(uv.val())) { 997 cover << uv.val(); 998 y << IntSet(0, x.size()); 999 } 1000 } 1001 1002 unshare(*gi.currentSpace, x); 1003 count(*gi.currentSpace, x, y, cover, GecodeSolverInstance::ann2icl(ann)); 1004} 1005 1006void p_global_cardinality_low_up_closed(SolverInstanceBase& s, const Call* call) { 1007 const Annotation& ann = call->ann(); 1008 auto& gi = static_cast<GecodeSolverInstance&>(s); 1009 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1010 IntArgs cover = GecodeSolverInstance::arg2intargs(call->arg(1)); 1011 1012 IntArgs lbound = GecodeSolverInstance::arg2intargs(call->arg(2)); 1013 IntArgs ubound = GecodeSolverInstance::arg2intargs(call->arg(3)); 1014 IntSetArgs y(cover.size()); 1015 for (int i = cover.size(); (i--) != 0;) { 1016 y[i] = IntSet(lbound[i], ubound[i]); 1017 } 1018 1019 unshare(*gi.currentSpace, x); 1020 count(*gi.currentSpace, x, y, cover, GecodeSolverInstance::ann2icl(ann)); 1021} 1022 1023void p_minimum(SolverInstanceBase& s, const Call* call) { 1024 const Annotation& ann = call->ann(); 1025 auto& gi = static_cast<GecodeSolverInstance&>(s); 1026 IntVarArgs iv = gi.arg2intvarargs(call->arg(1)); 1027 min(*gi.currentSpace, iv, gi.arg2intvar(call->arg(0)), GecodeSolverInstance::ann2icl(ann)); 1028} 1029 1030void p_maximum(SolverInstanceBase& s, const Call* call) { 1031 const Annotation& ann = call->ann(); 1032 auto& gi = static_cast<GecodeSolverInstance&>(s); 1033 IntVarArgs iv = gi.arg2intvarargs(call->arg(1)); 1034 max(*gi.currentSpace, iv, gi.arg2intvar(call->arg(0)), GecodeSolverInstance::ann2icl(ann)); 1035} 1036 1037void p_maximum_arg(SolverInstanceBase& s, const Call* call) { 1038 const Annotation& ann = call->ann(); 1039 auto& gi = static_cast<GecodeSolverInstance&>(s); 1040 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 1041 argmax(*gi.currentSpace, iv, gi.arg2intvar(call->arg(1)), true, 1042 GecodeSolverInstance::ann2icl(ann)); 1043} 1044 1045void p_minimum_arg(SolverInstanceBase& s, const Call* call) { 1046 const Annotation& ann = call->ann(); 1047 auto& gi = static_cast<GecodeSolverInstance&>(s); 1048 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 1049 argmin(*gi.currentSpace, iv, gi.arg2intvar(call->arg(1)), true, 1050 GecodeSolverInstance::ann2icl(ann)); 1051} 1052 1053void p_regular(SolverInstanceBase& s, const Call* call) { 1054 const Annotation& ann = call->ann(); 1055 auto& gi = static_cast<GecodeSolverInstance&>(s); 1056 IntVarArgs iv = gi.arg2intvarargs(call->arg(0)); 1057 int q = static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()); 1058 int symbols = static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()); 1059 IntArgs d = GecodeSolverInstance::arg2intargs(call->arg(3)); 1060 int q0 = static_cast<int>(call->arg(4)->cast<IntLit>()->v().toInt()); 1061 1062 int noOfTrans = 0; 1063 for (int i = 1; i <= q; i++) { 1064 for (int j = 1; j <= symbols; j++) { 1065 if (d[(i - 1) * symbols + (j - 1)] > 0) { 1066 noOfTrans++; 1067 } 1068 } 1069 } 1070 1071 Region re; 1072 auto* t = re.alloc<DFA::Transition>(noOfTrans + 1); 1073 noOfTrans = 0; 1074 for (int i = 1; i <= q; i++) { 1075 for (int j = 1; j <= symbols; j++) { 1076 if (d[(i - 1) * symbols + (j - 1)] > 0) { 1077 t[noOfTrans].i_state = i; 1078 t[noOfTrans].symbol = j; 1079 t[noOfTrans].o_state = d[(i - 1) * symbols + (j - 1)]; 1080 noOfTrans++; 1081 } 1082 } 1083 } 1084 t[noOfTrans].i_state = -1; 1085 1086 // Final states 1087 IntSetVal* isv = eval_intset(s.env().envi(), call->arg(5)); 1088 IntSetRanges isr(isv); 1089 1090 int* f = static_cast<int*>(malloc(sizeof(int) * (isv->card().toInt()) + 1)); 1091 int i = 0; 1092 for (Ranges::ToValues<IntSetRanges> val_iter(isr); val_iter(); ++val_iter, ++i) { 1093 f[i] = static_cast<int>(val_iter.val().toInt()); 1094 } 1095 f[i] = -1; 1096 1097 DFA dfa(q0, t, f); 1098 free(f); 1099 unshare(*gi.currentSpace, iv); 1100 extensional(*gi.currentSpace, iv, dfa, GecodeSolverInstance::ann2icl(ann)); 1101} 1102 1103void p_sort(SolverInstanceBase& s, const Call* call) { 1104 const Annotation& ann = call->ann(); 1105 auto& gi = static_cast<GecodeSolverInstance&>(s); 1106 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1107 IntVarArgs y = gi.arg2intvarargs(call->arg(1)); 1108 IntVarArgs xy(x.size() + y.size()); 1109 for (int i = x.size(); (i--) != 0;) { 1110 xy[i] = x[i]; 1111 } 1112 for (int i = y.size(); (i--) != 0;) { 1113 xy[i + x.size()] = y[i]; 1114 } 1115 unshare(*gi.currentSpace, xy); 1116 for (int i = x.size(); (i--) != 0;) { 1117 x[i] = xy[i]; 1118 } 1119 for (int i = y.size(); (i--) != 0;) { 1120 y[i] = xy[i + x.size()]; 1121 } 1122 sorted(*gi.currentSpace, x, y, GecodeSolverInstance::ann2icl(ann)); 1123} 1124 1125void p_inverse_offsets(SolverInstanceBase& s, const Call* call) { 1126 auto& gi = static_cast<GecodeSolverInstance&>(s); 1127 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1128 unshare(*gi.currentSpace, x); 1129 int xoff = static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()); 1130 IntVarArgs y = gi.arg2intvarargs(call->arg(2)); 1131 unshare(*gi.currentSpace, y); 1132 int yoff = static_cast<int>(call->arg(3)->cast<IntLit>()->v().toInt()); 1133 MZ_IntConLevel icl = GecodeSolverInstance::ann2icl(call->ann()); 1134 channel(*gi.currentSpace, x, xoff, y, yoff, icl == MZ_ICL_DEF ? MZ_ICL_DOM : icl); 1135} 1136 1137void p_increasing_int(SolverInstanceBase& s, const Call* call) { 1138 const Annotation& ann = call->ann(); 1139 auto& gi = static_cast<GecodeSolverInstance&>(s); 1140 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1141 rel(*gi.currentSpace, x, IRT_LQ, GecodeSolverInstance::ann2icl(ann)); 1142} 1143 1144void p_increasing_bool(SolverInstanceBase& s, const Call* call) { 1145 const Annotation& ann = call->ann(); 1146 auto& gi = static_cast<GecodeSolverInstance&>(s); 1147 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1148 rel(*gi.currentSpace, x, IRT_LQ, GecodeSolverInstance::ann2icl(ann)); 1149} 1150 1151void p_decreasing_int(SolverInstanceBase& s, const Call* call) { 1152 const Annotation& ann = call->ann(); 1153 auto& gi = static_cast<GecodeSolverInstance&>(s); 1154 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1155 rel(*gi.currentSpace, x, IRT_GQ, GecodeSolverInstance::ann2icl(ann)); 1156} 1157 1158void p_decreasing_bool(SolverInstanceBase& s, const Call* call) { 1159 const Annotation& ann = call->ann(); 1160 auto& gi = static_cast<GecodeSolverInstance&>(s); 1161 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1162 rel(*gi.currentSpace, x, IRT_GQ, GecodeSolverInstance::ann2icl(ann)); 1163} 1164 1165void p_table_int(SolverInstanceBase& s, const Call* call) { 1166 const Annotation& ann = call->ann(); 1167 auto& gi = static_cast<GecodeSolverInstance&>(s); 1168 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1169 IntArgs tuples = GecodeSolverInstance::arg2intargs(call->arg(1)); 1170 int noOfVars = x.size(); 1171 int noOfTuples = tuples.size() == 0 ? 0 : (tuples.size() / noOfVars); 1172 TupleSet ts(noOfVars); 1173 for (int i = 0; i < noOfTuples; i++) { 1174 IntArgs t(noOfVars); 1175 for (int j = 0; j < x.size(); j++) { 1176 t[j] = tuples[i * noOfVars + j]; 1177 } 1178 ts.add(t); 1179 } 1180 ts.finalize(); 1181 extensional(*gi.currentSpace, x, ts, GecodeSolverInstance::ann2icl(ann)); 1182} 1183void p_table_bool(SolverInstanceBase& s, const Call* call) { 1184 const Annotation& ann = call->ann(); 1185 auto& gi = static_cast<GecodeSolverInstance&>(s); 1186 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1187 IntArgs tuples = GecodeSolverInstance::arg2boolargs(call->arg(1)); 1188 int noOfVars = x.size(); 1189 int noOfTuples = tuples.size() == 0 ? 0 : (tuples.size() / noOfVars); 1190 TupleSet ts(noOfVars); 1191 for (int i = 0; i < noOfTuples; i++) { 1192 IntArgs t(noOfVars); 1193 for (int j = 0; j < x.size(); j++) { 1194 t[j] = tuples[i * noOfVars + j]; 1195 } 1196 ts.add(t); 1197 } 1198 ts.finalize(); 1199 extensional(*gi.currentSpace, x, ts, GecodeSolverInstance::ann2icl(ann)); 1200} 1201 1202void p_cumulatives(SolverInstanceBase& s, const Call* call) { 1203 const Annotation& ann = call->ann(); 1204 auto& gi = static_cast<GecodeSolverInstance&>(s); 1205 IntVarArgs start = gi.arg2intvarargs(call->arg(0)); 1206 IntVarArgs duration = gi.arg2intvarargs(call->arg(1)); 1207 IntVarArgs height = gi.arg2intvarargs(call->arg(2)); 1208 int n = start.size(); 1209 IntVar bound = gi.arg2intvar(call->arg(3)); 1210 1211 int minHeight = INT_MAX; 1212 int minHeight2 = INT_MAX; 1213 for (int i = n; (i--) != 0;) { 1214 if (height[i].min() < minHeight) { 1215 minHeight = height[i].min(); 1216 } else if (height[i].min() < minHeight2) { 1217 minHeight2 = height[i].min(); 1218 } 1219 } 1220 bool disjunctive = (minHeight > bound.max() / 2) || 1221 (minHeight2 > bound.max() / 2 && minHeight + minHeight2 > bound.max()); 1222 if (disjunctive) { 1223 rel(*gi.currentSpace, bound >= max(height)); 1224 // Unary 1225 if (duration.assigned()) { 1226 IntArgs durationI(n); 1227 for (int i = n; (i--) != 0;) { 1228 durationI[i] = duration[i].val(); 1229 } 1230 unshare(*gi.currentSpace, start); 1231 unary(*gi.currentSpace, start, durationI); 1232 } else { 1233 IntVarArgs end(n); 1234 for (int i = n; (i--) != 0;) { 1235 end[i] = expr(*gi.currentSpace, start[i] + duration[i]); 1236 } 1237 unshare(*gi.currentSpace, start); 1238 unary(*gi.currentSpace, start, duration, end); 1239 } 1240 } else if (height.assigned()) { 1241 IntArgs heightI(n); 1242 for (int i = n; (i--) != 0;) { 1243 heightI[i] = height[i].val(); 1244 } 1245 if (duration.assigned()) { 1246 IntArgs durationI(n); 1247 for (int i = n; (i--) != 0;) { 1248 durationI[i] = duration[i].val(); 1249 } 1250 cumulative(*gi.currentSpace, bound, start, durationI, heightI); 1251 } else { 1252 IntVarArgs end(n); 1253 for (int i = n; (i--) != 0;) { 1254 end[i] = expr(*gi.currentSpace, start[i] + duration[i]); 1255 } 1256 cumulative(*gi.currentSpace, bound, start, duration, end, heightI); 1257 } 1258 } else if (bound.assigned()) { 1259 IntArgs machine = IntArgs::create(n, 0, 0); 1260 IntArgs limit({bound.val()}); 1261 IntVarArgs end(n); 1262 for (int i = n; (i--) != 0;) { 1263 end[i] = expr(*gi.currentSpace, start[i] + duration[i]); 1264 } 1265 cumulatives(*gi.currentSpace, machine, start, duration, end, height, limit, true, 1266 GecodeSolverInstance::ann2icl(ann)); 1267 } else { 1268 int min = Gecode::Int::Limits::max; 1269 int max = Gecode::Int::Limits::min; 1270 IntVarArgs end(start.size()); 1271 for (int i = start.size(); (i--) != 0;) { 1272 min = std::min(min, start[i].min()); 1273 max = std::max(max, start[i].max() + duration[i].max()); 1274 end[i] = expr(*gi.currentSpace, start[i] + duration[i]); 1275 } 1276 for (int time = min; time < max; ++time) { 1277 IntVarArgs x(start.size()); 1278 for (int i = start.size(); (i--) != 0;) { 1279 IntVar overlaps = channel(*gi.currentSpace, 1280 expr(*gi.currentSpace, (start[i] <= time) && (time < end[i]))); 1281 x[i] = expr(*gi.currentSpace, overlaps * height[i]); 1282 } 1283 linear(*gi.currentSpace, x, IRT_LQ, bound); 1284 } 1285 } 1286} 1287 1288void p_among_seq_int(SolverInstanceBase& s, const Call* call) { 1289 const Annotation& ann = call->ann(); 1290 auto& gi = static_cast<GecodeSolverInstance&>(s); 1291 Gecode::IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1292 IntSet S = gi.arg2intset(s.env().envi(), call->arg(1)); 1293 int q = static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()); 1294 int l = static_cast<int>(call->arg(3)->cast<IntLit>()->v().toInt()); 1295 int u = static_cast<int>(call->arg(4)->cast<IntLit>()->v().toInt()); 1296 unshare(*gi.currentSpace, x); 1297 sequence(*gi.currentSpace, x, S, q, l, u, GecodeSolverInstance::ann2icl(ann)); 1298} 1299 1300void p_among_seq_bool(SolverInstanceBase& s, const Call* call) { 1301 const Annotation& ann = call->ann(); 1302 auto& gi = static_cast<GecodeSolverInstance&>(s); 1303 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1304 bool val = call->arg(1)->cast<BoolLit>()->v(); 1305 int q = static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()); 1306 int l = static_cast<int>(call->arg(3)->cast<IntLit>()->v().toInt()); 1307 int u = static_cast<int>(call->arg(4)->cast<IntLit>()->v().toInt()); 1308 IntSet S(static_cast<int>(val), static_cast<int>(val)); 1309 unshare(*gi.currentSpace, x); 1310 sequence(*gi.currentSpace, x, S, q, l, u, GecodeSolverInstance::ann2icl(ann)); 1311} 1312 1313void p_schedule_unary(SolverInstanceBase& s, const Call* call) { 1314 auto& gi = static_cast<GecodeSolverInstance&>(s); 1315 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1316 IntArgs p = GecodeSolverInstance::arg2intargs(call->arg(1)); 1317 unshare(*gi.currentSpace, x); 1318 unary(*gi.currentSpace, x, p); 1319} 1320 1321void p_schedule_unary_optional(SolverInstanceBase& s, const Call* call) { 1322 auto& gi = static_cast<GecodeSolverInstance&>(s); 1323 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1324 IntArgs p = GecodeSolverInstance::arg2intargs(call->arg(1)); 1325 BoolVarArgs m = gi.arg2boolvarargs(call->arg(2)); 1326 unshare(*gi.currentSpace, x); 1327 unary(*gi.currentSpace, x, p, m); 1328} 1329 1330void p_cumulative_opt(SolverInstanceBase& s, const Call* ce) { 1331 const Annotation& ann = ce->ann(); 1332 auto& gi = static_cast<GecodeSolverInstance&>(s); 1333 IntVarArgs start = gi.arg2intvarargs(ce->arg(0)); 1334 IntArgs duration = GecodeSolverInstance::arg2intargs(ce->arg(1)); 1335 IntArgs height = GecodeSolverInstance::arg2intargs(ce->arg(2)); 1336 BoolVarArgs opt = gi.arg2boolvarargs(ce->arg(3)); 1337 int bound = static_cast<int>(ce->arg(4)->cast<IntLit>()->v().toInt()); 1338 unshare(*gi.currentSpace, start); 1339 cumulative(*gi.currentSpace, bound, start, duration, height, opt, 1340 GecodeSolverInstance::ann2icl(ann)); 1341} 1342 1343void p_circuit(SolverInstanceBase& s, const Call* call) { 1344 const Annotation& ann = call->ann(); 1345 auto& gi = static_cast<GecodeSolverInstance&>(s); 1346 int off = static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()); 1347 IntVarArgs xv = gi.arg2intvarargs(call->arg(1)); 1348 unshare(*gi.currentSpace, xv); 1349 circuit(*gi.currentSpace, off, xv, GecodeSolverInstance::ann2icl(ann)); 1350} 1351void p_circuit_cost_array(SolverInstanceBase& s, const Call* call) { 1352 const Annotation& ann = call->ann(); 1353 auto& gi = static_cast<GecodeSolverInstance&>(s); 1354 IntArgs c = GecodeSolverInstance::arg2intargs(call->arg(0)); 1355 IntVarArgs xv = gi.arg2intvarargs(call->arg(1)); 1356 IntVarArgs yv = gi.arg2intvarargs(call->arg(2)); 1357 IntVar z = gi.arg2intvar(call->arg(3)); 1358 unshare(*gi.currentSpace, xv); 1359 circuit(*gi.currentSpace, c, xv, yv, z, GecodeSolverInstance::ann2icl(ann)); 1360} 1361void p_circuit_cost(SolverInstanceBase& s, const Call* call) { 1362 const Annotation& ann = call->ann(); 1363 auto& gi = static_cast<GecodeSolverInstance&>(s); 1364 IntArgs c = GecodeSolverInstance::arg2intargs(call->arg(0)); 1365 IntVarArgs xv = gi.arg2intvarargs(call->arg(1)); 1366 IntVar z = gi.arg2intvar(call->arg(2)); 1367 unshare(*gi.currentSpace, xv); 1368 circuit(*gi.currentSpace, c, xv, z, GecodeSolverInstance::ann2icl(ann)); 1369} 1370 1371void p_nooverlap(SolverInstanceBase& s, const Call* call) { 1372 const Annotation& ann = call->ann(); 1373 auto& gi = static_cast<GecodeSolverInstance&>(s); 1374 IntVarArgs x0 = gi.arg2intvarargs(call->arg(0)); 1375 IntVarArgs w = gi.arg2intvarargs(call->arg(1)); 1376 IntVarArgs y0 = gi.arg2intvarargs(call->arg(2)); 1377 IntVarArgs h = gi.arg2intvarargs(call->arg(3)); 1378 if (w.assigned() && h.assigned()) { 1379 IntArgs iw(w.size()); 1380 for (int i = w.size(); (i--) != 0;) { 1381 iw[i] = w[i].val(); 1382 } 1383 IntArgs ih(h.size()); 1384 for (int i = h.size(); (i--) != 0;) { 1385 ih[i] = h[i].val(); 1386 } 1387 nooverlap(*gi.currentSpace, x0, iw, y0, ih, GecodeSolverInstance::ann2icl(ann)); 1388 } else { 1389 IntVarArgs x1(x0.size()); 1390 IntVarArgs y1(y0.size()); 1391 for (int i = x0.size(); (i--) != 0;) { 1392 x1[i] = expr(*gi.currentSpace, x0[i] + w[i]); 1393 } 1394 for (int i = y0.size(); (i--) != 0;) { 1395 y1[i] = expr(*gi.currentSpace, y0[i] + h[i]); 1396 } 1397 nooverlap(*gi.currentSpace, x0, w, x1, y0, h, y1, GecodeSolverInstance::ann2icl(ann)); 1398 } 1399} 1400 1401void p_precede(SolverInstanceBase& s, const Call* call) { 1402 const Annotation& ann = call->ann(); 1403 auto& gi = static_cast<GecodeSolverInstance&>(s); 1404 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1405 int p_s = static_cast<int>(call->arg(1)->cast<IntLit>()->v().toInt()); 1406 int p_t = static_cast<int>(call->arg(2)->cast<IntLit>()->v().toInt()); 1407 precede(*gi.currentSpace, x, p_s, p_t, GecodeSolverInstance::ann2icl(ann)); 1408} 1409 1410void p_nvalue(SolverInstanceBase& s, const Call* call) { 1411 const Annotation& ann = call->ann(); 1412 auto& gi = static_cast<GecodeSolverInstance&>(s); 1413 IntVarArgs x = gi.arg2intvarargs(call->arg(1)); 1414 if (call->arg(0)->type().isvarint()) { 1415 IntVar y = gi.arg2intvar(call->arg(0)); 1416 nvalues(*gi.currentSpace, x, IRT_EQ, y, GecodeSolverInstance::ann2icl(ann)); 1417 } else { 1418 nvalues(*gi.currentSpace, x, IRT_EQ, 1419 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()), 1420 GecodeSolverInstance::ann2icl(ann)); 1421 } 1422} 1423 1424void p_among(SolverInstanceBase& s, const Call* call) { 1425 const Annotation& ann = call->ann(); 1426 auto& gi = static_cast<GecodeSolverInstance&>(s); 1427 IntVarArgs x = gi.arg2intvarargs(call->arg(1)); 1428 IntSet v = gi.arg2intset(s.env().envi(), call->arg(2)); 1429 if (call->arg(0)->type().isvarint()) { 1430 IntVar n = gi.arg2intvar(call->arg(0)); 1431 unshare(*gi.currentSpace, x); 1432 count(*gi.currentSpace, x, v, IRT_EQ, n, GecodeSolverInstance::ann2icl(ann)); 1433 } else { 1434 unshare(*gi.currentSpace, x); 1435 count(*gi.currentSpace, x, v, IRT_EQ, 1436 static_cast<int>(call->arg(0)->cast<IntLit>()->v().toInt()), 1437 GecodeSolverInstance::ann2icl(ann)); 1438 } 1439} 1440 1441void p_member_int(SolverInstanceBase& s, const Call* call) { 1442 const Annotation& ann = call->ann(); 1443 auto& gi = static_cast<GecodeSolverInstance&>(s); 1444 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1445 IntVar y = gi.arg2intvar(call->arg(1)); 1446 member(*gi.currentSpace, x, y, GecodeSolverInstance::ann2icl(ann)); 1447} 1448void p_member_int_reif(SolverInstanceBase& s, const Call* call) { 1449 const Annotation& ann = call->ann(); 1450 auto& gi = static_cast<GecodeSolverInstance&>(s); 1451 IntVarArgs x = gi.arg2intvarargs(call->arg(0)); 1452 IntVar y = gi.arg2intvar(call->arg(1)); 1453 BoolVar b = gi.arg2boolvar(call->arg(2)); 1454 member(*gi.currentSpace, x, y, b, GecodeSolverInstance::ann2icl(ann)); 1455} 1456void p_member_bool(SolverInstanceBase& s, const Call* call) { 1457 const Annotation& ann = call->ann(); 1458 auto& gi = static_cast<GecodeSolverInstance&>(s); 1459 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1460 BoolVar y = gi.arg2boolvar(call->arg(1)); 1461 member(*gi.currentSpace, x, y, GecodeSolverInstance::ann2icl(ann)); 1462} 1463void p_member_bool_reif(SolverInstanceBase& s, const Call* call) { 1464 const Annotation& ann = call->ann(); 1465 auto& gi = static_cast<GecodeSolverInstance&>(s); 1466 BoolVarArgs x = gi.arg2boolvarargs(call->arg(0)); 1467 BoolVar y = gi.arg2boolvar(call->arg(1)); 1468 member(*gi.currentSpace, x, y, gi.arg2boolvar(call->arg(2)), GecodeSolverInstance::ann2icl(ann)); 1469} 1470 1471// FLOAT CONSTRAINTS 1472#ifdef GECODE_HAS_FLOAT_VARS 1473 1474void p_int2float(SolverInstanceBase& s, const Call* ce) { 1475 auto& gi = static_cast<GecodeSolverInstance&>(s); 1476 IntVar x0 = gi.arg2intvar(ce->arg(0)); 1477 FloatVar x1 = gi.arg2floatvar(ce->arg(1)); 1478 channel(*gi.currentSpace, x0, x1); 1479} 1480 1481void p_float_lin_cmp(GecodeSolverInstance& s, FloatRelType frt, const Call* ce) { 1482 FloatValArgs fa = GecodeSolverInstance::arg2floatargs(ce->arg(0)); 1483 FloatVarArgs fv = s.arg2floatvarargs(ce->arg(1)); 1484 linear(*s.currentSpace, fa, fv, frt, ce->arg(2)->cast<FloatLit>()->v().toDouble()); 1485} 1486void p_float_lin_cmp_reif(GecodeSolverInstance& s, FloatRelType frt, const Call* ce) { 1487 FloatValArgs fa = GecodeSolverInstance::arg2floatargs(ce->arg(0)); 1488 FloatVarArgs fv = s.arg2floatvarargs(ce->arg(1)); 1489 linear(*s.currentSpace, fa, fv, frt, ce->arg(2)->cast<FloatLit>()->v().toDouble(), 1490 s.arg2boolvar(ce->arg(3))); 1491} 1492void p_float_lin_eq(SolverInstanceBase& s, const Call* ce) { 1493 auto& gi = static_cast<GecodeSolverInstance&>(s); 1494 p_float_lin_cmp(gi, FRT_EQ, ce); 1495} 1496void p_float_lin_eq_reif(SolverInstanceBase& s, const Call* ce) { 1497 auto& gi = static_cast<GecodeSolverInstance&>(s); 1498 p_float_lin_cmp_reif(gi, FRT_EQ, ce); 1499} 1500void p_float_lin_le(SolverInstanceBase& s, const Call* ce) { 1501 auto& gi = static_cast<GecodeSolverInstance&>(s); 1502 p_float_lin_cmp(gi, FRT_LQ, ce); 1503} 1504void p_float_lin_le_reif(SolverInstanceBase& s, const Call* ce) { 1505 auto& gi = static_cast<GecodeSolverInstance&>(s); 1506 p_float_lin_cmp_reif(gi, FRT_LQ, ce); 1507} 1508 1509void p_float_times(SolverInstanceBase& s, const Call* ce) { 1510 auto& gi = static_cast<GecodeSolverInstance&>(s); 1511 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1512 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1513 FloatVar z = gi.arg2floatvar(ce->arg(2)); 1514 mult(*gi.currentSpace, x, y, z); 1515} 1516 1517void p_float_div(SolverInstanceBase& s, const Call* ce) { 1518 auto& gi = static_cast<GecodeSolverInstance&>(s); 1519 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1520 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1521 FloatVar z = gi.arg2floatvar(ce->arg(2)); 1522 div(*gi.currentSpace, x, y, z); 1523} 1524 1525void p_float_plus(SolverInstanceBase& s, const Call* ce) { 1526 auto& gi = static_cast<GecodeSolverInstance&>(s); 1527 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1528 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1529 FloatVar z = gi.arg2floatvar(ce->arg(2)); 1530 rel(*gi.currentSpace, x + y == z); 1531} 1532 1533void p_float_sqrt(SolverInstanceBase& s, const Call* ce) { 1534 auto& gi = static_cast<GecodeSolverInstance&>(s); 1535 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1536 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1537 sqrt(*gi.currentSpace, x, y); 1538} 1539 1540void p_float_abs(SolverInstanceBase& s, const Call* ce) { 1541 auto& gi = static_cast<GecodeSolverInstance&>(s); 1542 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1543 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1544 abs(*gi.currentSpace, x, y); 1545} 1546 1547void p_float_eq(SolverInstanceBase& s, const Call* ce) { 1548 auto& gi = static_cast<GecodeSolverInstance&>(s); 1549 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1550 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1551 rel(*gi.currentSpace, x, FRT_EQ, y); 1552} 1553void p_float_eq_reif(SolverInstanceBase& s, const Call* ce) { 1554 auto& gi = static_cast<GecodeSolverInstance&>(s); 1555 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1556 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1557 BoolVar b = gi.arg2boolvar(ce->arg(2)); 1558 rel(*gi.currentSpace, x, FRT_EQ, y, b); 1559} 1560void p_float_le(SolverInstanceBase& s, const Call* ce) { 1561 auto& gi = static_cast<GecodeSolverInstance&>(s); 1562 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1563 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1564 rel(*gi.currentSpace, x, FRT_LQ, y); 1565} 1566void p_float_le_reif(SolverInstanceBase& s, const Call* ce) { 1567 auto& gi = static_cast<GecodeSolverInstance&>(s); 1568 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1569 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1570 BoolVar b = gi.arg2boolvar(ce->arg(2)); 1571 rel(*gi.currentSpace, x, FRT_LQ, y, b); 1572} 1573void p_float_max(SolverInstanceBase& s, const Call* ce) { 1574 auto& gi = static_cast<GecodeSolverInstance&>(s); 1575 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1576 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1577 FloatVar z = gi.arg2floatvar(ce->arg(2)); 1578 max(*gi.currentSpace, x, y, z); 1579} 1580void p_float_min(SolverInstanceBase& s, const Call* ce) { 1581 auto& gi = static_cast<GecodeSolverInstance&>(s); 1582 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1583 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1584 FloatVar z = gi.arg2floatvar(ce->arg(2)); 1585 min(*gi.currentSpace, x, y, z); 1586} 1587void p_float_lt(SolverInstanceBase& s, const Call* ce) { 1588 auto& gi = static_cast<GecodeSolverInstance&>(s); 1589 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1590 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1591 rel(*gi.currentSpace, x, FRT_LQ, y); 1592 rel(*gi.currentSpace, x, FRT_EQ, y, BoolVar(*gi.currentSpace, 0, 0)); 1593} 1594 1595void p_float_lt_reif(SolverInstanceBase& s, const Call* ce) { 1596 auto& gi = static_cast<GecodeSolverInstance&>(s); 1597 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1598 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1599 BoolVar b = gi.arg2boolvar(ce->arg(2)); 1600 BoolVar b0(*gi.currentSpace, 0, 1); 1601 BoolVar b1(*gi.currentSpace, 0, 1); 1602 rel(*gi.currentSpace, b == (b0 && !b1)); 1603 rel(*gi.currentSpace, x, FRT_LQ, y, b0); 1604 rel(*gi.currentSpace, x, FRT_EQ, y, b1); 1605} 1606 1607void p_float_ne(SolverInstanceBase& s, const Call* ce) { 1608 auto& gi = static_cast<GecodeSolverInstance&>(s); 1609 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1610 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1611 rel(*gi.currentSpace, x, FRT_EQ, y, BoolVar(*gi.currentSpace, 0, 0)); 1612} 1613 1614#ifdef GECODE_HAS_MPFR 1615#define P_FLOAT_OP(Op) \ 1616 void p_float_##Op(SolverInstanceBase& s, const Call* ce) { \ 1617 GecodeSolverInstance& gi = static_cast<GecodeSolverInstance&>(s); \ 1618 FloatVar x = gi.arg2floatvar(ce->arg(0)); \ 1619 FloatVar y = gi.arg2floatvar(ce->arg(1)); \ 1620 Op(*gi.currentSpace, x, y); \ 1621 } 1622P_FLOAT_OP(acos) 1623P_FLOAT_OP(asin) 1624P_FLOAT_OP(atan) 1625P_FLOAT_OP(cos) 1626P_FLOAT_OP(exp) 1627P_FLOAT_OP(sin) 1628P_FLOAT_OP(tan) 1629// P_FLOAT_OP(sinh) 1630// P_FLOAT_OP(tanh) 1631// P_FLOAT_OP(cosh) 1632#undef P_FLOAT_OP 1633 1634void p_float_ln(SolverInstanceBase& s, const Call* ce) { 1635 GecodeSolverInstance& gi = static_cast<GecodeSolverInstance&>(s); 1636 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1637 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1638 log(*gi.currentSpace, x, y); 1639} 1640void p_float_log10(SolverInstanceBase& s, const Call* ce) { 1641 GecodeSolverInstance& gi = static_cast<GecodeSolverInstance&>(s); 1642 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1643 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1644 log(*gi.currentSpace, 10.0, x, y); 1645} 1646void p_float_log2(SolverInstanceBase& s, const Call* ce) { 1647 GecodeSolverInstance& gi = static_cast<GecodeSolverInstance&>(s); 1648 FloatVar x = gi.arg2floatvar(ce->arg(0)); 1649 FloatVar y = gi.arg2floatvar(ce->arg(1)); 1650 log(*gi.currentSpace, 2.0, x, y); 1651} 1652 1653#endif 1654#endif 1655 1656#ifdef GECODE_HAS_SET_VARS 1657void p_set_op(SolverInstanceBase& s, SetOpType op, const Call* ce) { 1658 auto& gi = static_cast<GecodeSolverInstance&>(s); 1659 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), op, gi.arg2setvar(ce->arg(1)), SRT_EQ, 1660 gi.arg2setvar(ce->arg(2))); 1661} 1662void p_set_union(SolverInstanceBase& s, const Call* ce) { p_set_op(s, SOT_UNION, ce); } 1663void p_set_intersect(SolverInstanceBase& s, const Call* ce) { p_set_op(s, SOT_INTER, ce); } 1664void p_set_diff(SolverInstanceBase& s, const Call* ce) { p_set_op(s, SOT_MINUS, ce); } 1665 1666void p_set_symdiff(SolverInstanceBase& s, const Call* ce) { 1667 auto& gi = static_cast<GecodeSolverInstance&>(s); 1668 SetVar x = gi.arg2setvar(ce->arg(0)); 1669 SetVar y = gi.arg2setvar(ce->arg(1)); 1670 1671 SetVarLubRanges xub(x); 1672 IntSet xubs(xub); 1673 SetVar x_y(*gi.currentSpace, IntSet::empty, xubs); 1674 rel(*gi.currentSpace, x, SOT_MINUS, y, SRT_EQ, x_y); 1675 1676 SetVarLubRanges yub(y); 1677 IntSet yubs(yub); 1678 SetVar y_x(*gi.currentSpace, IntSet::empty, yubs); 1679 rel(*gi.currentSpace, y, SOT_MINUS, x, SRT_EQ, y_x); 1680 1681 rel(*gi.currentSpace, x_y, SOT_UNION, y_x, SRT_EQ, gi.arg2setvar(ce->arg(2))); 1682} 1683 1684void p_array_set_op(SolverInstanceBase& s, SetOpType op, const Call* ce) { 1685 auto& gi = static_cast<GecodeSolverInstance&>(s); 1686 SetVarArgs xs = gi.arg2setvarargs(ce->arg(0)); 1687 rel(*gi.currentSpace, op, xs, gi.arg2setvar(ce->arg(1))); 1688} 1689void p_array_set_union(SolverInstanceBase& s, const Call* ce) { p_array_set_op(s, SOT_UNION, ce); } 1690void p_array_set_partition(SolverInstanceBase& s, const Call* ce) { 1691 p_array_set_op(s, SOT_DUNION, ce); 1692} 1693 1694void p_set_rel(SolverInstanceBase& s, SetRelType srt, const Call* ce) { 1695 auto& gi = static_cast<GecodeSolverInstance&>(s); 1696 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), srt, gi.arg2setvar(ce->arg(1))); 1697} 1698 1699void p_set_eq(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_EQ, ce); } 1700void p_set_ne(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_NQ, ce); } 1701void p_set_subset(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_SUB, ce); } 1702void p_set_superset(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_SUP, ce); } 1703void p_set_le(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_LQ, ce); } 1704void p_set_lt(SolverInstanceBase& s, const Call* ce) { p_set_rel(s, SRT_LE, ce); } 1705void p_set_card(SolverInstanceBase& s, const Call* ce) { 1706 auto& gi = static_cast<GecodeSolverInstance&>(s); 1707 if (!ce->arg(1)->type().isvar()) { 1708 IntVal i = ce->arg(1)->cast<IntLit>()->v().toInt(); 1709 assert(i >= 0 && i <= Gecode::Int::Limits::max); 1710 auto ui = static_cast<unsigned int>(i.toInt()); 1711 cardinality(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), ui, ui); 1712 } else { 1713 cardinality(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), gi.arg2intvar(ce->arg(1))); 1714 } 1715} 1716void p_set_in(SolverInstanceBase& s, const Call* ce) { 1717 auto& gi = static_cast<GecodeSolverInstance&>(s); 1718 if (!ce->arg(1)->type().isvar()) { 1719 IntSet d = gi.arg2intset(s.env().envi(), ce->arg(1)); 1720 if (ce->arg(0)->type().isvar()) { 1721 Gecode::IntSetRanges dr(d); 1722 Iter::Ranges::Singleton sr(0, 1); 1723 Iter::Ranges::Inter<Gecode::IntSetRanges, Iter::Ranges::Singleton> i(dr, sr); 1724 IntSet d01(i); 1725 if (d01.size() == 0) { 1726 gi.currentSpace->fail(); 1727 } else { 1728 rel(*gi.currentSpace, gi.arg2boolvar(ce->arg(0)), IRT_GQ, d01.min()); 1729 rel(*gi.currentSpace, gi.arg2boolvar(ce->arg(0)), IRT_LQ, d01.max()); 1730 } 1731 } else { 1732 dom(*gi.currentSpace, gi.arg2intvar(ce->arg(0)), d); 1733 } 1734 } else { 1735 if (!ce->arg(0)->type().isvar()) { 1736 dom(*gi.currentSpace, gi.arg2setvar(ce->arg(1)), SRT_SUP, 1737 static_cast<int>(ce->arg(0)->cast<IntLit>()->v().toInt())); 1738 } else { 1739 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(1)), SRT_SUP, gi.arg2intvar(ce->arg(0))); 1740 } 1741 } 1742} 1743void p_set_rel_reif(SolverInstanceBase& s, SetRelType srt, const Call* ce) { 1744 auto& gi = static_cast<GecodeSolverInstance&>(s); 1745 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), srt, gi.arg2setvar(ce->arg(1)), 1746 gi.arg2boolvar(ce->arg(2))); 1747} 1748 1749void p_set_eq_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_EQ, ce); } 1750void p_set_le_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_LQ, ce); } 1751void p_set_lt_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_LE, ce); } 1752void p_set_ne_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_NQ, ce); } 1753void p_set_subset_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_SUB, ce); } 1754void p_set_superset_reif(SolverInstanceBase& s, const Call* ce) { p_set_rel_reif(s, SRT_SUP, ce); } 1755void p_set_in_reif(SolverInstanceBase& s, const Call* ce, ReifyMode rm) { 1756 auto& gi = static_cast<GecodeSolverInstance&>(s); 1757 if (!ce->arg(1)->type().isvar()) { 1758 if (rm == RM_EQV) { 1759 p_int_in_reif(s, ce); 1760 } else { 1761 assert(rm == RM_IMP); 1762 p_int_in_imp(s, ce); 1763 } 1764 } else { 1765 if (!ce->arg(0)->type().isvar()) { 1766 dom(*gi.currentSpace, gi.arg2setvar(ce->arg(1)), SRT_SUP, 1767 static_cast<int>(ce->arg(0)->cast<IntLit>()->v().toInt()), 1768 Reify(gi.arg2boolvar(ce->arg(2)), rm)); 1769 } else { 1770 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(1)), SRT_SUP, gi.arg2intvar(ce->arg(0)), 1771 Reify(gi.arg2boolvar(ce->arg(2)), rm)); 1772 } 1773 } 1774} 1775void p_set_in_reif(SolverInstanceBase& s, const Call* ce) { p_set_in_reif(s, ce, RM_EQV); } 1776void p_set_in_imp(SolverInstanceBase& s, const Call* ce) { p_set_in_reif(s, ce, RM_IMP); } 1777void p_set_disjoint(SolverInstanceBase& s, const Call* ce) { 1778 auto& gi = static_cast<GecodeSolverInstance&>(s); 1779 rel(*gi.currentSpace, gi.arg2setvar(ce->arg(0)), SRT_DISJ, gi.arg2setvar(ce->arg(1))); 1780} 1781 1782void p_link_set_to_booleans(SolverInstanceBase& s, const Call* ce) { 1783 auto& gi = static_cast<GecodeSolverInstance&>(s); 1784 SetVar x = gi.arg2setvar(ce->arg(0)); 1785 int idx = static_cast<int>(ce->arg(2)->cast<IntLit>()->v().toInt()); 1786 assert(idx >= 0); 1787 rel(*gi.currentSpace, x || IntSet(Set::Limits::min, idx - 1)); 1788 BoolVarArgs y = gi.arg2boolvarargs(ce->arg(1), idx); 1789 unshare(*gi.currentSpace, y); 1790 channel(*gi.currentSpace, y, x); 1791} 1792 1793void p_array_set_element(SolverInstanceBase& s, const Call* ce) { 1794 auto& gi = static_cast<GecodeSolverInstance&>(s); 1795 bool isConstant = true; 1796 ArrayLit* a = gi.arg2arraylit(ce->arg(1)); 1797 for (unsigned int i = a->size(); (i--) != 0U;) { 1798 if ((*a)[i]->type().isvar()) { 1799 isConstant = false; 1800 break; 1801 } 1802 } 1803 IntVar selector = gi.arg2intvar(ce->arg(0)); 1804 rel(*gi.currentSpace, selector > 0); 1805 if (isConstant) { 1806 IntSetArgs sv = gi.arg2intsetargs(gi.env().envi(), ce->arg(1), 1); 1807 element(*gi.currentSpace, sv, selector, gi.arg2setvar(ce->arg(2))); 1808 } else { 1809 SetVarArgs sv = gi.arg2setvarargs(ce->arg(1), 1); 1810 element(*gi.currentSpace, sv, selector, gi.arg2setvar(ce->arg(2))); 1811 } 1812} 1813 1814void p_array_set_element_op(SolverInstanceBase& s, const Call* ce, SetOpType op, 1815 const IntSet& universe = IntSet(Set::Limits::min, Set::Limits::max)) { 1816 auto& gi = static_cast<GecodeSolverInstance&>(s); 1817 bool isConstant = true; 1818 ArrayLit* a = gi.arg2arraylit(ce->arg(1)); 1819 for (unsigned int i = a->size(); (i--) != 0;) { 1820 if ((*a)[i]->type().isvar()) { 1821 isConstant = false; 1822 break; 1823 } 1824 } 1825 SetVar selector = gi.arg2setvar(ce->arg(0)); 1826 dom(*gi.currentSpace, selector, SRT_DISJ, 0); 1827 if (isConstant) { 1828 IntSetArgs sv = gi.arg2intsetargs(gi.env().envi(), ce->arg(1), 1); 1829 element(*gi.currentSpace, op, sv, selector, gi.arg2setvar(ce->arg(2)), universe); 1830 } else { 1831 SetVarArgs sv = gi.arg2setvarargs(ce->arg(1), 1); 1832 element(*gi.currentSpace, op, sv, selector, gi.arg2setvar(ce->arg(2)), universe); 1833 } 1834} 1835 1836void p_array_set_element_union(SolverInstanceBase& s, const Call* ce) { 1837 p_array_set_element_op(s, ce, SOT_UNION); 1838} 1839 1840void p_array_set_element_intersect(SolverInstanceBase& s, const Call* ce) { 1841 p_array_set_element_op(s, ce, SOT_INTER); 1842} 1843 1844void p_array_set_element_intersect_in(SolverInstanceBase& s, const Call* ce) { 1845 auto& gi = static_cast<GecodeSolverInstance&>(s); 1846 IntSet d = gi.arg2intset(gi.env().envi(), ce->arg(3)); 1847 p_array_set_element_op(s, ce, SOT_INTER, d); 1848} 1849 1850void p_array_set_element_partition(SolverInstanceBase& s, const Call* ce) { 1851 p_array_set_element_op(s, ce, SOT_DUNION); 1852} 1853 1854void p_set_convex(SolverInstanceBase& s, const Call* ce) { 1855 auto& gi = static_cast<GecodeSolverInstance&>(s); 1856 convex(*gi.currentSpace, gi.arg2setvar(ce->arg(0))); 1857} 1858 1859void p_array_set_seq(SolverInstanceBase& s, const Call* ce) { 1860 auto& gi = static_cast<GecodeSolverInstance&>(s); 1861 SetVarArgs sv = gi.arg2setvarargs(ce->arg(0)); 1862 sequence(*gi.currentSpace, sv); 1863} 1864 1865void p_array_set_seq_union(SolverInstanceBase& s, const Call* ce) { 1866 auto& gi = static_cast<GecodeSolverInstance&>(s); 1867 SetVarArgs sv = gi.arg2setvarargs(ce->arg(0)); 1868 sequence(*gi.currentSpace, sv, gi.arg2setvar(ce->arg(1))); 1869} 1870 1871void p_int_set_channel(SolverInstanceBase& s, const Call* ce) { 1872 auto& gi = static_cast<GecodeSolverInstance&>(s); 1873 int xoff = static_cast<int>(ce->arg(1)->cast<IntLit>()->v().toInt()); 1874 assert(xoff >= 0); 1875 int yoff = static_cast<int>(ce->arg(3)->cast<IntLit>()->v().toInt()); 1876 assert(yoff >= 0); 1877 IntVarArgs xv = gi.arg2intvarargs(ce->arg(0), xoff); 1878 SetVarArgs yv = gi.arg2setvarargs(ce->arg(2), yoff, 1, IntSet(0, xoff - 1)); 1879 IntSet xd(yoff, yv.size() - 1); 1880 for (int i = xoff; i < xv.size(); i++) { 1881 dom(*gi.currentSpace, xv[i], xd); 1882 } 1883 IntSet yd(xoff, xv.size() - 1); 1884 for (int i = yoff; i < yv.size(); i++) { 1885 dom(*gi.currentSpace, yv[i], SRT_SUB, yd); 1886 } 1887 channel(*gi.currentSpace, xv, yv); 1888} 1889 1890void p_range(SolverInstanceBase& s, const Call* ce) { 1891 auto& gi = static_cast<GecodeSolverInstance&>(s); 1892 int xoff = static_cast<int>(ce->arg(1)->cast<IntLit>()->v().toInt()); 1893 assert(xoff >= 0); 1894 IntVarArgs xv = gi.arg2intvarargs(ce->arg(0), xoff); 1895 element(*gi.currentSpace, SOT_UNION, xv, gi.arg2setvar(ce->arg(2)), gi.arg2setvar(ce->arg(3))); 1896} 1897 1898void p_weights(SolverInstanceBase& s, const Call* ce) { 1899 auto& gi = static_cast<GecodeSolverInstance&>(s); 1900 IntArgs e = GecodeSolverInstance::arg2intargs(ce->arg(0)); 1901 IntArgs w = GecodeSolverInstance::arg2intargs(ce->arg(1)); 1902 SetVar x = gi.arg2setvar(ce->arg(2)); 1903 IntVar y = gi.arg2intvar(ce->arg(3)); 1904 weights(*gi.currentSpace, e, w, x, y); 1905} 1906 1907void p_inverse_set(SolverInstanceBase& s, const Call* ce) { 1908 auto& gi = static_cast<GecodeSolverInstance&>(s); 1909 int xoff = static_cast<int>(ce->arg(2)->cast<IntLit>()->v().toInt()); 1910 int yoff = static_cast<int>(ce->arg(3)->cast<IntLit>()->v().toInt()); 1911 SetVarArgs x = gi.arg2setvarargs(ce->arg(0), xoff); 1912 SetVarArgs y = gi.arg2setvarargs(ce->arg(1), yoff); 1913 channel(*gi.currentSpace, x, y); 1914} 1915 1916void p_precede_set(SolverInstanceBase& s, const Call* ce) { 1917 auto& gi = static_cast<GecodeSolverInstance&>(s); 1918 SetVarArgs x = gi.arg2setvarargs(ce->arg(0)); 1919 int p_s = static_cast<int>(ce->arg(1)->cast<IntLit>()->v().toInt()); 1920 int p_t = static_cast<int>(ce->arg(2)->cast<IntLit>()->v().toInt()); 1921 precede(*gi.currentSpace, x, p_s, p_t); 1922} 1923#endif 1924 1925} // namespace GecodeConstraints 1926 1927} // namespace MiniZinc