27 model_ =
new CpModelProto();
28 constant_map_ =
new Dictionary<long, int>();
33 public CpModelProto
Model 35 get {
return model_; }
38 int Negated(
int index)
47 return new IntVar(model_,
new Domain(lb, ub), name);
52 return new IntVar(model_, domain, name);
59 return new IntVar(model_,
new Domain(value), String.Format(
"{0}", value));
64 return new IntVar(model_,
new Domain(value), name);
69 return new IntVar(model_,
new Domain(0, 1), name);
80 Dictionary<IntVar, long> dict =
new Dictionary<IntVar, long>();
83 LinearConstraintProto linear =
new LinearConstraintProto();
84 foreach (KeyValuePair<IntVar, long> term
in dict)
86 linear.Vars.Add(term.Key.Index);
87 linear.Coeffs.Add(term.Value);
89 foreach (
long value
in domain.FlattenedIntervals())
91 if (value == Int64.MinValue || value == Int64.MaxValue)
93 linear.Domain.Add(value);
97 linear.Domain.Add(value - constant);
100 ct.Proto.Linear = linear;
120 Domain.FromFlatIntervals(
new long[] { Int64.MinValue, -1, 1,
126 new Domain(lin.
Lb, lin.
Lb));
132 Domain.FromFlatIntervals(
133 new long[] { Int64.MinValue, lin.Lb - 1, lin.Lb + 1, Int64.MaxValue }));
142 AllDifferentConstraintProto alldiff =
new AllDifferentConstraintProto();
143 foreach (
IntVar var
in vars)
145 alldiff.Vars.Add(var.
Index);
147 ct.Proto.AllDiff = alldiff;
155 ElementConstraintProto element =
new ElementConstraintProto();
156 element.Index = index.
Index;
157 foreach (
IntVar var
in vars)
159 element.Vars.Add(var.
Index);
161 element.Target = target.Index;
162 ct.Proto.Element = element;
170 ElementConstraintProto element =
new ElementConstraintProto();
171 element.Index = index.
Index;
172 foreach (
long value
in values)
174 element.Vars.Add(ConvertConstant(value));
176 element.Target = target.Index;
177 ct.Proto.Element = element;
185 ElementConstraintProto element =
new ElementConstraintProto();
186 element.Index = index.
Index;
187 foreach (
int value
in values)
189 element.Vars.Add(ConvertConstant(value));
191 element.Target = target.Index;
192 ct.Proto.Element = element;
199 CircuitConstraintProto circuit =
new CircuitConstraintProto();
200 foreach (var arc
in arcs)
202 circuit.Tails.Add(arc.Item1);
203 circuit.Heads.Add(arc.Item2);
204 circuit.Literals.Add(arc.Item3.GetIndex());
206 ct.Proto.Circuit = circuit;
214 TableConstraintProto table =
new TableConstraintProto();
215 foreach (
IntVar var
in vars)
217 table.Vars.Add(var.
Index);
219 for (
int i = 0; i < tuples.GetLength(0); ++i)
221 for (
int j = 0; j < tuples.GetLength(1); ++j)
223 table.Values.Add(tuples[i, j]);
226 ct.Proto.Table = table;
234 ct.
Proto.Table.Negated =
true;
241 IEnumerable<long> final_states)
244 AutomatonConstraintProto aut =
new AutomatonConstraintProto();
245 foreach (
IntVar var
in vars)
247 aut.Vars.Add(var.
Index);
249 aut.StartingState = starting_state;
250 foreach (
long f
in final_states)
252 aut.FinalStates.Add(f);
254 for (
int i = 0; i < transitions.GetLength(0); ++i)
256 aut.TransitionTail.Add(transitions[i, 0]);
257 aut.TransitionLabel.Add(transitions[i, 1]);
258 aut.TransitionHead.Add(transitions[i, 2]);
261 ct.Proto.Automaton = aut;
266 IEnumerable<IntVar> vars,
268 IEnumerable<Tuple<long, long, long>> transitions,
269 IEnumerable<long> final_states)
272 AutomatonConstraintProto aut =
new AutomatonConstraintProto();
273 foreach (
IntVar var
in vars)
275 aut.Vars.Add(var.
Index);
277 aut.StartingState = starting_state;
278 foreach (
long f
in final_states)
280 aut.FinalStates.Add(f);
282 foreach (Tuple<long, long, long> transition
in transitions)
285 aut.TransitionHead.Add(transition.Item1);
286 aut.TransitionLabel.Add(transition.Item2);
287 aut.TransitionTail.Add(transition.Item3);
290 ct.Proto.Automaton = aut;
295 IEnumerable<IntVar> reverse)
298 InverseConstraintProto inverse =
new InverseConstraintProto();
299 foreach (
IntVar var
in direct)
301 inverse.FDirect.Add(var.
Index);
303 foreach (
IntVar var
in reverse)
305 inverse.FInverse.Add(var.
Index);
307 ct.Proto.Inverse = inverse;
312 IEnumerable<I> demands,
313 long min_level,
long max_level)
316 ReservoirConstraintProto res =
new ReservoirConstraintProto();
317 foreach (
IntVar var
in times)
319 res.Times.Add(var.
Index);
321 foreach (I d
in demands)
323 res.Demands.Add(Convert.ToInt64(d));
326 ct.Proto.Reservoir = res;
331 IEnumerable<IntVar> times,
332 IEnumerable<I> demands,
333 IEnumerable<IntVar> actives,
334 long min_level,
long max_level)
337 ReservoirConstraintProto res =
new ReservoirConstraintProto();
338 foreach (
IntVar var
in times)
340 res.Times.Add(var.
Index);
342 foreach (I d
in demands)
344 res.Demands.Add(Convert.ToInt64(d));
346 foreach (
IntVar var
in actives)
348 res.Actives.Add(var.
Index);
351 ct.Proto.Reservoir = res;
356 IntVar var, IEnumerable<IntVar> bool_vars,
long offset = 0)
359 foreach (
IntVar bool_var
in bool_vars)
361 int b_index = bool_var.
Index;
362 int var_index = var.
Index;
364 ConstraintProto ct1 =
new ConstraintProto();
365 LinearConstraintProto lin1 =
new LinearConstraintProto();
366 lin1.Vars.Add(var_index);
368 lin1.Domain.Add(offset + i);
369 lin1.Domain.Add(offset + i);
371 ct1.EnforcementLiteral.Add(b_index);
372 model_.Constraints.Add(ct1);
374 ConstraintProto ct2 =
new ConstraintProto();
375 LinearConstraintProto lin2 =
new LinearConstraintProto();
376 lin2.Vars.Add(var_index);
378 lin2.Domain.Add(Int64.MinValue);
379 lin2.Domain.Add(offset + i - 1);
380 lin2.Domain.Add(offset + i + 1);
381 lin2.Domain.Add(Int64.MaxValue);
383 ct2.EnforcementLiteral.Add(-b_index - 1);
384 model_.Constraints.Add(ct2);
393 BoolArgumentProto or =
new BoolArgumentProto();
396 ct.
Proto.BoolOr = or;
403 BoolArgumentProto bool_argument =
new BoolArgumentProto();
406 bool_argument.Literals.Add(lit.
GetIndex());
408 ct.Proto.BoolOr = bool_argument;
415 BoolArgumentProto bool_argument =
new BoolArgumentProto();
418 bool_argument.Literals.Add(lit.
GetIndex());
420 ct.Proto.BoolAnd = bool_argument;
427 BoolArgumentProto bool_argument =
new BoolArgumentProto();
430 bool_argument.Literals.Add(lit.
GetIndex());
432 ct.Proto.BoolXor = bool_argument;
439 IntegerArgumentProto args =
new IntegerArgumentProto();
440 foreach (
IntVar var
in vars)
442 args.Vars.Add(var.
Index);
444 args.Target = target.Index;
445 ct.Proto.IntMin = args;
452 IntegerArgumentProto args =
new IntegerArgumentProto();
453 foreach (
IntVar var
in vars)
455 args.Vars.Add(var.
Index);
457 args.Target = target.Index;
458 ct.Proto.IntMax = args;
465 IntegerArgumentProto args =
new IntegerArgumentProto();
466 args.Vars.Add(GetOrCreateIndex(num));
467 args.Vars.Add(GetOrCreateIndex(denom));
468 args.Target = GetOrCreateIndex(target);
469 ct.
Proto.IntDiv = args;
476 IntegerArgumentProto args =
new IntegerArgumentProto();
477 args.Vars.Add(var.
Index);
478 args.Vars.Add(-var.
Index - 1);
479 args.Target = target.
Index;
480 ct.
Proto.IntMax = args;
487 IntegerArgumentProto args =
new IntegerArgumentProto();
488 args.Vars.Add(GetOrCreateIndex(v));
489 args.Vars.Add(GetOrCreateIndex(m));
490 args.Target = GetOrCreateIndex(target);
491 ct.
Proto.IntMod = args;
498 IntegerArgumentProto args =
new IntegerArgumentProto();
499 args.Target = target.
Index;
500 foreach (
IntVar var
in vars)
502 args.Vars.Add(var.
Index);
504 ct.Proto.IntProd = args;
511 S start, D duration, E end,
string name)
514 GetOrCreateIndex(start),
515 GetOrCreateIndex(duration),
516 GetOrCreateIndex(end),
522 S start, D duration, E end,
ILiteral is_present,
string name)
526 GetOrCreateIndex(start),
527 GetOrCreateIndex(duration),
528 GetOrCreateIndex(end),
536 NoOverlapConstraintProto args =
new NoOverlapConstraintProto();
541 ct.Proto.NoOverlap = args;
546 IEnumerable<IntervalVar> y_intervals)
549 NoOverlap2DConstraintProto args =
new NoOverlap2DConstraintProto();
552 args.XIntervals.Add(var.
GetIndex());
556 args.YIntervals.Add(var.
GetIndex());
558 ct.Proto.NoOverlap2D = args;
563 IEnumerable<D> demands,
567 CumulativeConstraintProto cumul =
new CumulativeConstraintProto();
570 cumul.Intervals.Add(var.
GetIndex());
572 foreach (D demand
in demands)
574 cumul.Demands.Add(GetOrCreateIndex(demand));
576 cumul.Capacity = GetOrCreateIndex(capacity);
577 ct.Proto.Cumulative = cumul;
585 SetObjective(obj,
true);
590 SetObjective(obj,
false);
595 SetObjective(
null,
true);
600 SetObjective(
null,
false);
605 if ((Object)var ==
null)
return;
606 model_.Objective.Vars.Add(var.
Index);
607 model_.Objective.Coeffs.Add(model_.Objective.ScalingFactor > 0 ? 1 : -1);
612 if (coeff == 0 || (Object)var ==
null)
return;
613 model_.Objective.Vars.Add(var.
Index);
614 model_.Objective.Coeffs.Add(model_.Objective.ScalingFactor > 0 ? coeff : -coeff);
619 return model_.Objective ==
null;
625 DecisionStrategyProto.Types.VariableSelectionStrategy var_str,
626 DecisionStrategyProto.Types.DomainReductionStrategy dom_str)
628 DecisionStrategyProto ds =
new DecisionStrategyProto();
629 foreach (
IntVar var
in vars)
631 ds.Variables.Add(var.
Index);
633 ds.VariableSelectionStrategy = var_str;
634 ds.DomainReductionStrategy = dom_str;
635 model_.SearchStrategy.Add(ds);
640 if (model_.SolutionHint ==
null) {
641 model_.SolutionHint =
new PartialVariableAssignment();
643 model_.SolutionHint.Vars.Add(var.
GetIndex());
644 model_.SolutionHint.Values.Add(value);
649 void SetObjective(
LinearExpr obj,
bool minimize)
651 CpObjectiveProto objective =
new CpObjectiveProto();
654 objective.Offset = 0L;
655 objective.ScalingFactor = minimize ? 1L : -1;
657 else if (obj is IntVar)
659 objective.Offset = 0L;
660 objective.Vars.Add(obj.
Index);
663 objective.Coeffs.Add(1L);
664 objective.ScalingFactor = 1L;
668 objective.Coeffs.Add(-1L);
669 objective.ScalingFactor = -1L;
674 Dictionary<IntVar, long> dict =
new Dictionary<IntVar, long>();
675 long constant = LinearExpr.GetVarValueMap(obj, 1L, dict);
678 objective.ScalingFactor = 1L;
679 objective.Offset = constant;
683 objective.ScalingFactor = -1L;
684 objective.Offset = -constant;
686 foreach (KeyValuePair<IntVar, long> it
in dict)
688 objective.Vars.Add(it.Key.Index);
689 objective.Coeffs.Add(minimize ? it.Value : -it.Value);
692 model_.Objective = objective;
705 private int ConvertConstant(
long value)
707 if (constant_map_.ContainsKey(value))
709 return constant_map_[value];
713 int index = model_.Variables.Count;
714 IntegerVariableProto var =
new IntegerVariableProto();
715 var.Domain.Add(value);
716 var.Domain.Add(value);
717 constant_map_.Add(value, index);
718 model_.Variables.Add(var);
723 private int GetOrCreateIndex<X>(X x)
725 if (typeof(X) == typeof(IntVar))
727 IntVar vx = (IntVar)(Object)x;
730 if (typeof(X) == typeof(
long) || typeof(X) == typeof(
int))
732 return ConvertConstant(Convert.ToInt64(x));
734 throw new ArgumentException(
"Cannot extract index from argument");
737 private CpModelProto model_;
738 private Dictionary<long, int> constant_map_;