OR-Tools  9.1
cp_model.cc
Go to the documentation of this file.
1 // Copyright 2010-2021 Google LLC
2 // Licensed under the Apache License, Version 2.0 (the "License");
3 // you may not use this file except in compliance with the License.
4 // You may obtain a copy of the License at
5 //
6 // http://www.apache.org/licenses/LICENSE-2.0
7 //
8 // Unless required by applicable law or agreed to in writing, software
9 // distributed under the License is distributed on an "AS IS" BASIS,
10 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 // See the License for the specific language governing permissions and
12 // limitations under the License.
13 
14 #include "ortools/sat/cp_model.h"
15 
16 #include <cstdint>
17 #include <limits>
18 
19 #include "absl/strings/str_format.h"
20 #include "ortools/base/map_util.h"
25 
26 namespace operations_research {
27 namespace sat {
28 
29 BoolVar::BoolVar() : cp_model_(nullptr), index_(0) {}
30 
31 BoolVar::BoolVar(int index, CpModelProto* cp_model)
32  : cp_model_(cp_model), index_(index) {}
33 
34 BoolVar BoolVar::WithName(const std::string& name) {
35  cp_model_->mutable_variables(index_)->set_name(name);
36  return *this;
37 }
38 
39 std::string BoolVar::DebugString() const {
40  if (index_ < 0) {
41  return absl::StrFormat("Not(%s)", Not().DebugString());
42  } else {
43  std::string output;
44  const IntegerVariableProto& var_proto = cp_model_->variables(index_);
45  // Special case for constant variables without names.
46  if (var_proto.name().empty() && var_proto.domain_size() == 2 &&
47  var_proto.domain(0) == var_proto.domain(1)) {
48  output.append(var_proto.domain(0) == 0 ? "false" : "true");
49  } else {
50  if (var_proto.name().empty()) {
51  absl::StrAppendFormat(&output, "BoolVar%i(", index_);
52  } else {
53  absl::StrAppendFormat(&output, "%s(", var_proto.name());
54  }
55  if (var_proto.domain(0) == var_proto.domain(1)) {
56  output.append(var_proto.domain(0) == 0 ? "false)" : "true)");
57  } else {
58  absl::StrAppend(&output, var_proto.domain(0), ", ", var_proto.domain(1),
59  ")");
60  }
61  }
62  return output;
63  }
64 }
65 
66 BoolVar Not(BoolVar x) { return x.Not(); }
67 
68 std::ostream& operator<<(std::ostream& os, const BoolVar& var) {
69  os << var.DebugString();
70  return os;
71 }
72 
73 IntVar::IntVar() : cp_model_(nullptr), index_(0) {}
74 
75 IntVar::IntVar(int index, CpModelProto* cp_model)
76  : cp_model_(cp_model), index_(index) {
78 }
79 
80 IntVar IntVar::WithName(const std::string& name) {
81  cp_model_->mutable_variables(index_)->set_name(name);
82  return *this;
83 }
84 
86  cp_model_ = var.cp_model_;
87  index_ = var.index_;
88 }
89 
91  CHECK_EQ(2, Proto().domain_size());
92  CHECK_GE(Proto().domain(0), 0);
93  CHECK_LE(Proto().domain(1), 1);
94  BoolVar var;
95  var.cp_model_ = cp_model_;
96  var.index_ = index();
97  return var;
98 }
99 
101  return LinearExpr(*this).AddConstant(value);
102 }
103 
104 std::string IntVar::DebugString() const {
105  if (index_ < 0) {
106  return absl::StrFormat("Not(%s)",
107  IntVar(NegatedRef(index_), cp_model_).DebugString());
108  }
109  const IntegerVariableProto& var_proto = cp_model_->variables(index_);
110  // Special case for constant variables without names.
111  if (var_proto.name().empty() && var_proto.domain_size() == 2 &&
112  var_proto.domain(0) == var_proto.domain(1)) {
113  return absl::StrCat(var_proto.domain(0));
114  } else {
115  std::string output;
116  if (var_proto.name().empty()) {
117  absl::StrAppend(&output, "IntVar", index_, "(");
118  } else {
119  absl::StrAppend(&output, var_proto.name(), "(");
120  }
121  if (var_proto.domain_size() == 2 &&
122  var_proto.domain(0) == var_proto.domain(1)) {
123  absl::StrAppend(&output, var_proto.domain(0), ")");
124  } else {
125  // TODO(user): Use domain pretty print function.
126  absl::StrAppend(&output, var_proto.domain(0), ", ", var_proto.domain(1),
127  ")");
128  }
129  return output;
130  }
131 }
132 
133 std::ostream& operator<<(std::ostream& os, const IntVar& var) {
134  os << var.DebugString();
135  return os;
136 }
137 
139 
141 
143 
144 LinearExpr::LinearExpr(int64_t constant) { constant_ = constant; }
145 
146 LinearExpr LinearExpr::Sum(absl::Span<const IntVar> vars) {
147  LinearExpr result;
148  for (const IntVar& var : vars) {
149  result.AddVar(var);
150  }
151  return result;
152 }
153 
154 LinearExpr LinearExpr::ScalProd(absl::Span<const IntVar> vars,
155  absl::Span<const int64_t> coeffs) {
156  CHECK_EQ(vars.size(), coeffs.size());
157  LinearExpr result;
158  for (int i = 0; i < vars.size(); ++i) {
159  result.AddTerm(vars[i], coeffs[i]);
160  }
161  return result;
162 }
163 
165  LinearExpr result;
166  result.AddTerm(var, coefficient);
167  return result;
168 }
169 
170 LinearExpr LinearExpr::BooleanSum(absl::Span<const BoolVar> vars) {
171  LinearExpr result;
172  for (const BoolVar& var : vars) {
173  result.AddVar(var);
174  }
175  return result;
176 }
177 
178 LinearExpr LinearExpr::BooleanScalProd(absl::Span<const BoolVar> vars,
179  absl::Span<const int64_t> coeffs) {
180  CHECK_EQ(vars.size(), coeffs.size());
181  LinearExpr result;
182  for (int i = 0; i < vars.size(); ++i) {
183  result.AddTerm(vars[i], coeffs[i]);
184  }
185  return result;
186 }
187 
189  constant_ += value;
190  return *this;
191 }
192 
194  AddTerm(var, 1);
195  return *this;
196 }
197 
199  const int index = var.index_;
200  if (RefIsPositive(index)) {
201  variables_.push_back(var);
202  coefficients_.push_back(coeff);
203  } else {
204  variables_.push_back(IntVar(PositiveRef(var.index_), var.cp_model_));
205  coefficients_.push_back(-coeff);
206  constant_ += coeff;
207  }
208  return *this;
209 }
210 
212  constant_ += expr.constant_;
213  variables_.insert(variables_.end(), expr.variables_.begin(),
214  expr.variables_.end());
215  coefficients_.insert(coefficients_.end(), expr.coefficients_.begin(),
216  expr.coefficients_.end());
217  return *this;
218 }
219 
221  CHECK_EQ(constant_, 0);
222  CHECK_EQ(1, variables_.size());
223  CHECK_EQ(1, coefficients_[0]);
224  return variables_.front();
225 }
226 
227 int64_t LinearExpr::Value() const {
228  CHECK(variables_.empty());
229  return constant_;
230 }
231 
232 std::string LinearExpr::DebugString() const {
233  std::string result;
234  for (int i = 0; i < variables_.size(); ++i) {
235  const int64_t coeff = coefficients_[i];
236  if (i == 0) {
237  if (coeff == 1) {
238  absl::StrAppend(&result, variables_[i].DebugString());
239  } else if (coeff == -1) {
240  absl::StrAppend(&result, "-", variables_[i].DebugString());
241  } else if (coeff != 0) {
242  absl::StrAppend(&result, coeff, " * ", variables_[i].DebugString());
243  }
244  } else if (coeff == 1) {
245  absl::StrAppend(&result, " + ", variables_[i].DebugString());
246  } else if (coeff > 0) {
247  absl::StrAppend(&result, " + ", coeff, " * ",
248  variables_[i].DebugString());
249  } else if (coeff == -1) {
250  absl::StrAppend(&result, " - ", variables_[i].DebugString());
251  } else if (coeff < 0) {
252  absl::StrAppend(&result, " - ", -coeff, " * ",
253  variables_[i].DebugString());
254  }
255  }
256 
257  if (constant_ != 0) {
258  if (variables_.empty()) {
259  return absl::StrCat(constant_);
260  } else if (constant_ > 0) {
261  absl::StrAppend(&result, " + ", constant_);
262  } else {
263  absl::StrAppend(&result, " - ", -constant_);
264  }
265  }
266  return result;
267 }
268 
269 std::ostream& operator<<(std::ostream& os, const LinearExpr& e) {
270  os << e.DebugString();
271  return os;
272 }
273 
275 
276 Constraint Constraint::WithName(const std::string& name) {
277  proto_->set_name(name);
278  return *this;
279 }
280 
281 const std::string& Constraint::Name() const { return proto_->name(); }
282 
283 Constraint Constraint::OnlyEnforceIf(absl::Span<const BoolVar> literals) {
284  for (const BoolVar& var : literals) {
286  }
287  return *this;
288 }
289 
292  return *this;
293 }
294 
299 }
300 
305 }
306 
307 void TableConstraint::AddTuple(absl::Span<const int64_t> tuple) {
308  CHECK_EQ(tuple.size(), proto_->table().vars_size());
309  for (const int64_t t : tuple) {
311  }
312 }
313 
314 ReservoirConstraint::ReservoirConstraint(ConstraintProto* proto,
315  CpModelBuilder* builder)
316  : Constraint(proto), builder_(builder) {}
317 
320  builder_->GetOrCreateIntegerIndex(time.index_));
322  proto_->mutable_reservoir()->add_actives(builder_->IndexFromConstant(1));
323 }
324 
326  BoolVar is_active) {
328  builder_->GetOrCreateIntegerIndex(time.index_));
330  proto_->mutable_reservoir()->add_actives(is_active.index_);
331 }
332 
334  int64_t transition_label) {
337  proto_->mutable_automaton()->add_transition_label(transition_label);
338 }
339 
341  IntervalVar y_coordinate) {
342  proto_->mutable_no_overlap_2d()->add_x_intervals(x_coordinate.index_);
343  proto_->mutable_no_overlap_2d()->add_y_intervals(y_coordinate.index_);
344 }
345 
346 CumulativeConstraint::CumulativeConstraint(ConstraintProto* proto,
347  CpModelBuilder* builder)
348  : Constraint(proto), builder_(builder) {}
349 
353  builder_->GetOrCreateIntegerIndex(demand.index_));
354 }
355 
356 IntervalVar::IntervalVar() : cp_model_(nullptr), index_() {}
357 
359  : cp_model_(cp_model), index_(index) {}
360 
362  cp_model_->mutable_constraints(index_)->set_name(name);
363  return *this;
364 }
365 
367  return CpModelBuilder::LinearExprFromProto(Proto().start_view(), cp_model_);
368 }
369 
371  return CpModelBuilder::LinearExprFromProto(Proto().size_view(), cp_model_);
372 }
373 
375  return CpModelBuilder::LinearExprFromProto(Proto().end_view(), cp_model_);
376 }
377 
379  return BoolVar(cp_model_->constraints(index_).enforcement_literal(0),
380  cp_model_);
381 }
382 
383 std::string IntervalVar::Name() const {
384  return cp_model_->constraints(index_).name();
385 }
386 
387 std::string IntervalVar::DebugString() const {
388  CHECK_GE(index_, 0);
389  const ConstraintProto& ct_proto = cp_model_->constraints(index_);
390  std::string output;
391  if (ct_proto.name().empty()) {
392  absl::StrAppend(&output, "IntervalVar", index_, "(");
393  } else {
394  absl::StrAppend(&output, ct_proto.name(), "(");
395  }
396  absl::StrAppend(&output, StartExpr().DebugString(), ", ",
397  SizeExpr().DebugString(), ", ", EndExpr().DebugString(), ", ",
398  PresenceBoolVar().DebugString(), ")");
399  return output;
400 }
401 
402 std::ostream& operator<<(std::ostream& os, const IntervalVar& var) {
403  os << var.DebugString();
404  return os;
405 }
406 
407 int CpModelBuilder::IndexFromConstant(int64_t value) {
408  if (!gtl::ContainsKey(constant_to_index_map_, value)) {
409  const int index = cp_model_.variables_size();
410  IntegerVariableProto* const var_proto = cp_model_.add_variables();
411  var_proto->add_domain(value);
412  var_proto->add_domain(value);
413  constant_to_index_map_[value] = index;
414  }
415  return constant_to_index_map_[value];
416 }
417 
418 int CpModelBuilder::GetOrCreateIntegerIndex(int index) {
419  if (index >= 0) {
420  return index;
421  }
422  if (!gtl::ContainsKey(bool_to_integer_index_map_, index)) {
423  const int var = PositiveRef(index);
424  const IntegerVariableProto& old_var = cp_model_.variables(var);
425  const int new_index = cp_model_.variables_size();
426  IntegerVariableProto* const new_var = cp_model_.add_variables();
427  new_var->add_domain(0);
428  new_var->add_domain(1);
429  if (!old_var.name().empty()) {
430  new_var->set_name(absl::StrCat("Not(", old_var.name(), ")"));
431  }
432  AddEquality(IntVar(new_index, &cp_model_), BoolVar(index, &cp_model_));
433  bool_to_integer_index_map_[index] = new_index;
434  return new_index;
435  }
436  return bool_to_integer_index_map_[index];
437 }
438 
440  const int index = cp_model_.variables_size();
441  IntegerVariableProto* const var_proto = cp_model_.add_variables();
442  for (const auto& interval : domain) {
443  var_proto->add_domain(interval.start);
444  var_proto->add_domain(interval.end);
445  }
446  return IntVar(index, &cp_model_);
447 }
448 
450  const int index = cp_model_.variables_size();
451  IntegerVariableProto* const var_proto = cp_model_.add_variables();
452  var_proto->add_domain(0);
453  var_proto->add_domain(1);
454  return BoolVar(index, &cp_model_);
455 }
456 
458  return IntVar(IndexFromConstant(value), &cp_model_);
459 }
460 
462  return BoolVar(IndexFromConstant(1), &cp_model_);
463 }
464 
466  return BoolVar(IndexFromConstant(0), &cp_model_);
467 }
468 
470  const LinearExpr& size,
471  const LinearExpr& end) {
472  return NewOptionalIntervalVar(start, size, end, TrueVar());
473 }
474 
476  int64_t size) {
477  return NewOptionalFixedSizeIntervalVar(start, size, TrueVar());
478 }
479 
481  const LinearExpr& size,
482  const LinearExpr& end,
483  BoolVar presence) {
484  AddEquality(LinearExpr(start).AddExpression(size), end)
485  .OnlyEnforceIf(presence);
486 
487  const int index = cp_model_.constraints_size();
488  ConstraintProto* const ct = cp_model_.add_constraints();
489  ct->add_enforcement_literal(presence.index_);
490  IntervalConstraintProto* const interval = ct->mutable_interval();
491  LinearExprToProto(start, interval->mutable_start_view());
492  LinearExprToProto(size, interval->mutable_size_view());
493  LinearExprToProto(end, interval->mutable_end_view());
494  return IntervalVar(index, &cp_model_);
495 }
496 
498  const LinearExpr& start, int64_t size, BoolVar presence) {
499  const int index = cp_model_.constraints_size();
500  ConstraintProto* const ct = cp_model_.add_constraints();
501  ct->add_enforcement_literal(presence.index_);
502  IntervalConstraintProto* const interval = ct->mutable_interval();
503  LinearExprToProto(start, interval->mutable_start_view());
504  interval->mutable_size_view()->set_offset(size);
505  LinearExprToProto(start, interval->mutable_end_view());
506  interval->mutable_end_view()->set_offset(interval->end_view().offset() +
507  size);
508  return IntervalVar(index, &cp_model_);
509 }
510 
511 Constraint CpModelBuilder::AddBoolOr(absl::Span<const BoolVar> literals) {
512  ConstraintProto* const proto = cp_model_.add_constraints();
513  for (const BoolVar& lit : literals) {
514  proto->mutable_bool_or()->add_literals(lit.index_);
515  }
516  return Constraint(proto);
517 }
518 
519 Constraint CpModelBuilder::AddBoolAnd(absl::Span<const BoolVar> literals) {
520  ConstraintProto* const proto = cp_model_.add_constraints();
521  for (const BoolVar& lit : literals) {
522  proto->mutable_bool_and()->add_literals(lit.index_);
523  }
524  return Constraint(proto);
525 }
526 
527 Constraint CpModelBuilder::AddBoolXor(absl::Span<const BoolVar> literals) {
528  ConstraintProto* const proto = cp_model_.add_constraints();
529  for (const BoolVar& lit : literals) {
530  proto->mutable_bool_xor()->add_literals(lit.index_);
531  }
532  return Constraint(proto);
533 }
534 
535 void CpModelBuilder::FillLinearTerms(const LinearExpr& left,
536  const LinearExpr& right,
538  for (const IntVar& x : left.variables()) {
539  proto->add_vars(x.index_);
540  }
541  for (const int64_t coeff : left.coefficients()) {
542  proto->add_coeffs(coeff);
543  }
544  for (const IntVar& x : right.variables()) {
545  proto->add_vars(x.index_);
546  }
547  for (const int64_t coeff : right.coefficients()) {
548  proto->add_coeffs(-coeff);
549  }
550 }
551 
553  const LinearExpr& right) {
554  ConstraintProto* const proto = cp_model_.add_constraints();
555  FillLinearTerms(left, right, proto->mutable_linear());
556  const int64_t rhs = right.constant() - left.constant();
557  proto->mutable_linear()->add_domain(rhs);
558  proto->mutable_linear()->add_domain(rhs);
559  return Constraint(proto);
560 }
561 
563  const LinearExpr& right) {
564  ConstraintProto* const proto = cp_model_.add_constraints();
565  FillLinearTerms(left, right, proto->mutable_linear());
566  const int64_t rhs = right.constant() - left.constant();
567  proto->mutable_linear()->add_domain(rhs);
568  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::max());
569  return Constraint(proto);
570 }
571 
573  const LinearExpr& right) {
574  ConstraintProto* const proto = cp_model_.add_constraints();
575  FillLinearTerms(left, right, proto->mutable_linear());
576  const int64_t rhs = right.constant() - left.constant();
577  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::min());
578  proto->mutable_linear()->add_domain(rhs);
579  return Constraint(proto);
580 }
581 
583  const LinearExpr& right) {
584  ConstraintProto* const proto = cp_model_.add_constraints();
585  FillLinearTerms(left, right, proto->mutable_linear());
586  const int64_t rhs = right.constant() - left.constant();
587  proto->mutable_linear()->add_domain(rhs + 1);
588  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::max());
589  return Constraint(proto);
590 }
591 
593  const LinearExpr& right) {
594  ConstraintProto* const proto = cp_model_.add_constraints();
595  FillLinearTerms(left, right, proto->mutable_linear());
596  const int64_t rhs = right.constant() - left.constant();
597  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::min());
598  proto->mutable_linear()->add_domain(rhs - 1);
599  return Constraint(proto);
600 }
601 
603  const Domain& domain) {
604  ConstraintProto* const proto = cp_model_.add_constraints();
605  for (const IntVar& x : expr.variables()) {
606  proto->mutable_linear()->add_vars(x.index_);
607  }
608  for (const int64_t coeff : expr.coefficients()) {
609  proto->mutable_linear()->add_coeffs(coeff);
610  }
611  const int64_t cst = expr.constant();
612  for (const auto& i : domain) {
613  proto->mutable_linear()->add_domain(i.start - cst);
614  proto->mutable_linear()->add_domain(i.end - cst);
615  }
616  return Constraint(proto);
617 }
618 
620  const LinearExpr& right) {
621  ConstraintProto* const proto = cp_model_.add_constraints();
622  FillLinearTerms(left, right, proto->mutable_linear());
623  const int64_t rhs = right.constant() - left.constant();
624  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::min());
625  proto->mutable_linear()->add_domain(rhs - 1);
626  proto->mutable_linear()->add_domain(rhs + 1);
627  proto->mutable_linear()->add_domain(std::numeric_limits<int64_t>::max());
628  return Constraint(proto);
629 }
630 
631 Constraint CpModelBuilder::AddAllDifferent(absl::Span<const IntVar> vars) {
632  ConstraintProto* const proto = cp_model_.add_constraints();
633  for (const IntVar& var : vars) {
634  proto->mutable_all_diff()->add_vars(GetOrCreateIntegerIndex(var.index_));
635  }
636  return Constraint(proto);
637 }
638 
640  IntVar index, absl::Span<const IntVar> variables, IntVar target) {
641  ConstraintProto* const proto = cp_model_.add_constraints();
642  proto->mutable_element()->set_index(GetOrCreateIntegerIndex(index.index_));
643  proto->mutable_element()->set_target(GetOrCreateIntegerIndex(target.index_));
644  for (const IntVar& var : variables) {
645  proto->mutable_element()->add_vars(GetOrCreateIntegerIndex(var.index_));
646  }
647  return Constraint(proto);
648 }
649 
651  absl::Span<const int64_t> values,
652  IntVar target) {
653  ConstraintProto* const proto = cp_model_.add_constraints();
654  proto->mutable_element()->set_index(GetOrCreateIntegerIndex(index.index_));
655  proto->mutable_element()->set_target(GetOrCreateIntegerIndex(target.index_));
656  for (int64_t value : values) {
657  proto->mutable_element()->add_vars(IndexFromConstant(value));
658  }
659  return Constraint(proto);
660 }
661 
663  return CircuitConstraint(cp_model_.add_constraints());
664 }
665 
667  return MultipleCircuitConstraint(cp_model_.add_constraints());
668 }
669 
671  absl::Span<const IntVar> vars) {
672  ConstraintProto* const proto = cp_model_.add_constraints();
673  for (const IntVar& var : vars) {
674  proto->mutable_table()->add_vars(GetOrCreateIntegerIndex(var.index_));
675  }
676  return TableConstraint(proto);
677 }
678 
680  absl::Span<const IntVar> vars) {
681  ConstraintProto* const proto = cp_model_.add_constraints();
682  for (const IntVar& var : vars) {
683  proto->mutable_table()->add_vars(GetOrCreateIntegerIndex(var.index_));
684  }
685  proto->mutable_table()->set_negated(true);
686  return TableConstraint(proto);
687 }
688 
690  absl::Span<const IntVar> variables,
691  absl::Span<const IntVar> inverse_variables) {
692  ConstraintProto* const proto = cp_model_.add_constraints();
693  for (const IntVar& var : variables) {
694  proto->mutable_inverse()->add_f_direct(GetOrCreateIntegerIndex(var.index_));
695  }
696  for (const IntVar& var : inverse_variables) {
697  proto->mutable_inverse()->add_f_inverse(
698  GetOrCreateIntegerIndex(var.index_));
699  }
700  return Constraint(proto);
701 }
702 
704  int64_t max_level) {
705  ConstraintProto* const proto = cp_model_.add_constraints();
706  proto->mutable_reservoir()->set_min_level(min_level);
707  proto->mutable_reservoir()->set_max_level(max_level);
708  return ReservoirConstraint(proto, this);
709 }
710 
712  absl::Span<const IntVar> transition_variables, int starting_state,
713  absl::Span<const int> final_states) {
714  ConstraintProto* const proto = cp_model_.add_constraints();
715  for (const IntVar& var : transition_variables) {
716  proto->mutable_automaton()->add_vars(GetOrCreateIntegerIndex(var.index_));
717  }
718  proto->mutable_automaton()->set_starting_state(starting_state);
719  for (const int final_state : final_states) {
720  proto->mutable_automaton()->add_final_states(final_state);
721  }
722  return AutomatonConstraint(proto);
723 }
724 
726  absl::Span<const IntVar> vars) {
727  ConstraintProto* const proto = cp_model_.add_constraints();
728  proto->mutable_int_min()->set_target(GetOrCreateIntegerIndex(target.index_));
729  for (const IntVar& var : vars) {
730  proto->mutable_int_min()->add_vars(GetOrCreateIntegerIndex(var.index_));
731  }
732  return Constraint(proto);
733 }
734 
735 void CpModelBuilder::LinearExprToProto(const LinearExpr& expr,
736  LinearExpressionProto* expr_proto) {
737  for (const IntVar var : expr.variables()) {
738  expr_proto->add_vars(GetOrCreateIntegerIndex(var.index_));
739  }
740  for (const int64_t coeff : expr.coefficients()) {
741  expr_proto->add_coeffs(coeff);
742  }
743  expr_proto->set_offset(expr.constant());
744 }
745 
746 LinearExpr CpModelBuilder::LinearExprFromProto(
747  const LinearExpressionProto& expr_proto, CpModelProto* model_proto) {
748  LinearExpr result(expr_proto.offset());
749  for (int i = 0; i < expr_proto.vars_size(); ++i) {
750  result.AddTerm(IntVar(expr_proto.vars(i), model_proto),
751  expr_proto.coeffs(i));
752  }
753  return result;
754 }
755 
757  const LinearExpr& target, absl::Span<const LinearExpr> exprs) {
758  ConstraintProto* const proto = cp_model_.add_constraints();
759  LinearExprToProto(target, proto->mutable_lin_min()->mutable_target());
760  for (const LinearExpr& expr : exprs) {
761  LinearExpressionProto* expr_proto = proto->mutable_lin_min()->add_exprs();
762  LinearExprToProto(expr, expr_proto);
763  }
764  return Constraint(proto);
765 }
766 
768  absl::Span<const IntVar> vars) {
769  ConstraintProto* const proto = cp_model_.add_constraints();
770  proto->mutable_int_max()->set_target(GetOrCreateIntegerIndex(target.index_));
771  for (const IntVar& var : vars) {
772  proto->mutable_int_max()->add_vars(GetOrCreateIntegerIndex(var.index_));
773  }
774  return Constraint(proto);
775 }
776 
778  const LinearExpr& target, absl::Span<const LinearExpr> exprs) {
779  ConstraintProto* const proto = cp_model_.add_constraints();
780  LinearExprToProto(target, proto->mutable_lin_max()->mutable_target());
781  for (const LinearExpr& expr : exprs) {
782  LinearExpressionProto* expr_proto = proto->mutable_lin_max()->add_exprs();
783  LinearExprToProto(expr, expr_proto);
784  }
785  return Constraint(proto);
786 }
787 
789  IntVar denominator) {
790  ConstraintProto* const proto = cp_model_.add_constraints();
791  proto->mutable_int_div()->set_target(GetOrCreateIntegerIndex(target.index_));
792  proto->mutable_int_div()->add_vars(GetOrCreateIntegerIndex(numerator.index_));
793  proto->mutable_int_div()->add_vars(
794  GetOrCreateIntegerIndex(denominator.index_));
795  return Constraint(proto);
796 }
797 
799  ConstraintProto* const proto = cp_model_.add_constraints();
800  proto->mutable_int_max()->set_target(GetOrCreateIntegerIndex(target.index_));
801  proto->mutable_int_max()->add_vars(GetOrCreateIntegerIndex(var.index_));
802  proto->mutable_int_max()->add_vars(
803  NegatedRef(GetOrCreateIntegerIndex(var.index_)));
804  return Constraint(proto);
805 }
806 
808  IntVar mod) {
809  ConstraintProto* const proto = cp_model_.add_constraints();
810  proto->mutable_int_mod()->set_target(GetOrCreateIntegerIndex(target.index_));
811  proto->mutable_int_mod()->add_vars(GetOrCreateIntegerIndex(var.index_));
812  proto->mutable_int_mod()->add_vars(GetOrCreateIntegerIndex(mod.index_));
813  return Constraint(proto);
814 }
815 
817  absl::Span<const IntVar> vars) {
818  ConstraintProto* const proto = cp_model_.add_constraints();
819  proto->mutable_int_prod()->set_target(GetOrCreateIntegerIndex(target.index_));
820  for (const IntVar& var : vars) {
821  proto->mutable_int_prod()->add_vars(GetOrCreateIntegerIndex(var.index_));
822  }
823  return Constraint(proto);
824 }
825 
826 Constraint CpModelBuilder::AddNoOverlap(absl::Span<const IntervalVar> vars) {
827  ConstraintProto* const proto = cp_model_.add_constraints();
828  for (const IntervalVar& var : vars) {
829  proto->mutable_no_overlap()->add_intervals(
830  GetOrCreateIntegerIndex(var.index_));
831  }
832  return Constraint(proto);
833 }
834 
836  return NoOverlap2DConstraint(cp_model_.add_constraints());
837 }
838 
840  ConstraintProto* const proto = cp_model_.add_constraints();
841  proto->mutable_cumulative()->set_capacity(
842  GetOrCreateIntegerIndex(capacity.index_));
843  return CumulativeConstraint(proto, this);
844 }
845 
847  cp_model_.mutable_objective()->Clear();
848  for (const IntVar& x : expr.variables()) {
849  cp_model_.mutable_objective()->add_vars(x.index_);
850  }
851  for (const int64_t coeff : expr.coefficients()) {
852  cp_model_.mutable_objective()->add_coeffs(coeff);
853  }
854  cp_model_.mutable_objective()->set_offset(expr.constant());
855 }
856 
858  cp_model_.mutable_objective()->Clear();
859  for (const IntVar& x : expr.variables()) {
860  cp_model_.mutable_objective()->add_vars(x.index_);
861  }
862  for (const int64_t coeff : expr.coefficients()) {
863  cp_model_.mutable_objective()->add_coeffs(-coeff);
864  }
865  cp_model_.mutable_objective()->set_offset(-expr.constant());
866  cp_model_.mutable_objective()->set_scaling_factor(-1.0);
867 }
868 
869 void CpModelBuilder::ScaleObjectiveBy(double scaling) {
870  CHECK(cp_model_.has_objective());
872  scaling * cp_model_.objective().scaling_factor());
873 }
874 
876  absl::Span<const IntVar> variables,
879  DecisionStrategyProto* const proto = cp_model_.add_search_strategy();
880  for (const IntVar& var : variables) {
881  proto->add_variables(var.index_);
882  }
883  proto->set_variable_selection_strategy(var_strategy);
884  proto->set_domain_reduction_strategy(domain_strategy);
885 }
886 
888  absl::Span<const BoolVar> variables,
891  DecisionStrategyProto* const proto = cp_model_.add_search_strategy();
892  for (const BoolVar& var : variables) {
893  proto->add_variables(var.index_);
894  }
895  proto->set_variable_selection_strategy(var_strategy);
896  proto->set_domain_reduction_strategy(domain_strategy);
897 }
898 
900  cp_model_.mutable_solution_hint()->add_vars(
901  GetOrCreateIntegerIndex(var.index_));
902  cp_model_.mutable_solution_hint()->add_values(value);
903 }
904 
906  cp_model_.mutable_solution_hint()->Clear();
907 }
908 
910  cp_model_.mutable_assumptions()->Add(lit.index_);
911 }
912 
913 void CpModelBuilder::AddAssumptions(absl::Span<const BoolVar> literals) {
914  for (const BoolVar& lit : literals) {
915  cp_model_.mutable_assumptions()->Add(lit.index_);
916  }
917 }
918 
920  cp_model_.mutable_assumptions()->Clear();
921 }
922 
924  cp_model_ = model_proto;
925  // Rebuild constant to index map.
926  constant_to_index_map_.clear();
927  for (int i = 0; i < cp_model_.variables_size(); ++i) {
928  const IntegerVariableProto& var = cp_model_.variables(i);
929  if (var.domain_size() == 2 && var.domain(0) == var.domain(1)) {
930  constant_to_index_map_[var.domain(0)] = i;
931  }
932  }
933  // This one would be more complicated to rebuild. Let's just clear it.
934  bool_to_integer_index_map_.clear();
935 }
936 
938  CHECK_GE(index, 0);
939  CHECK_LT(index, cp_model_.variables_size());
940  const IntegerVariableProto& proto = cp_model_.variables(index);
941  CHECK_EQ(2, proto.domain_size())
942  << "CpModelBuilder::GetBoolVarFromProtoIndex: The domain of the variable "
943  "is not Boolean";
944  CHECK_GE(0, proto.domain(0))
945  << "CpModelBuilder::GetBoolVarFromProtoIndex: The domain of the variable "
946  "is not Boolean";
947  CHECK_LE(1, proto.domain(1))
948  << "CpModelBuilder::GetBoolVarFromProtoIndex: The domain of the variable "
949  "is not Boolean";
950  return BoolVar(index, &cp_model_);
951 }
952 
954  CHECK_GE(index, 0);
955  CHECK_LT(index, cp_model_.variables_size());
956  return IntVar(index, &cp_model_);
957 }
958 
960  CHECK_GE(index, 0);
961  CHECK_LT(index, cp_model_.constraints_size());
962  const ConstraintProto& ct = cp_model_.constraints(index);
963  CHECK_EQ(ct.constraint_case(), ConstraintProto::kInterval)
964  << "CpModelBuilder::GetIntervalVarFromProtoIndex: the referenced "
965  "object is not an interval variable";
966  return IntervalVar(index, &cp_model_);
967 }
968 
970  const LinearExpr& expr) {
971  int64_t result = expr.constant();
972  const std::vector<IntVar>& variables = expr.variables();
973  const std::vector<int64_t>& coefficients = expr.coefficients();
974  for (int i = 0; i < variables.size(); ++i) {
975  result += r.solution(variables[i].index_) * coefficients[i];
976  }
977  return result;
978 }
979 
981  if (r.solution_size() > 0) {
982  return r.solution(x.index_);
983  } else {
984  return r.solution_lower_bounds(x.index_);
985  }
986 }
987 
989  if (r.solution_size() > 0) {
990  return r.solution(x.index_);
991  } else {
992  return r.solution_upper_bounds(x.index_);
993  }
994 }
995 
997  const int ref = x.index_;
998  if (RefIsPositive(ref)) {
999  return r.solution(ref) == 1;
1000  } else {
1001  return r.solution(PositiveRef(ref)) == 0;
1002  }
1003 }
1004 
1005 } // namespace sat
1006 } // namespace operations_research
int64_t head
void AddArc(int tail, int head, BoolVar literal)
Add an arc to the circuit.
Definition: cp_model.cc:301
#define CHECK(condition)
Definition: base/logging.h:491
void add_tails(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8346
BoolVar FalseVar()
Creates an always false Boolean variable.
Definition: cp_model.cc:465
IntervalVar NewOptionalFixedSizeIntervalVar(const LinearExpr &start, int64_t size, BoolVar presence)
Creates an optional interval variable with a fixed size.
Definition: cp_model.cc:497
Constraint AddModuloEquality(IntVar target, IntVar var, IntVar mod)
Adds target = var % mod.
Definition: cp_model.cc:807
const ::operations_research::sat::TableConstraintProto & table() const
void add_actives(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8295
LinearExpr & AddConstant(int64_t value)
Adds a constant value to the linear expression.
Definition: cp_model.cc:188
Specialized reservoir constraint.
Definition: cp_model.h:532
LinearExpr EndExpr() const
Returns the end linear expression.
Definition: cp_model.cc:374
BoolVar TrueVar()
Creates an always true Boolean variable.
Definition: cp_model.cc:461
Constraint AddLinMaxEquality(const LinearExpr &target, absl::Span< const LinearExpr > exprs)
Adds target == max(exprs).
Definition: cp_model.cc:777
int64_t min
Definition: alldiff_cst.cc:139
void AddAssumption(BoolVar lit)
Adds a literal to the model as assumptions.
Definition: cp_model.cc:909
int64_t SolutionIntegerValue(const CpSolverResponse &r, const LinearExpr &expr)
Evaluates the value of an linear expression in a solver response.
Definition: cp_model.cc:969
std::string DebugString() const
Debug string.
Definition: cp_model.cc:39
Constraint AddAbsEquality(IntVar target, IntVar var)
Adds target == abs(var).
Definition: cp_model.cc:798
static LinearExpr Term(IntVar var, int64_t coefficient)
Constructs var * coefficient.
Definition: cp_model.cc:164
::PROTOBUF_NAMESPACE_ID::int64 solution_upper_bounds(int index) const
CircuitConstraint AddCircuitConstraint()
Adds a circuit constraint.
Definition: cp_model.cc:662
void add_enforcement_literal(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:9275
Constraint AddGreaterThan(const LinearExpr &left, const LinearExpr &right)
Adds left > right.
Definition: cp_model.cc:582
Specialized no_overlap2D constraint.
Definition: cp_model.h:580
#define CHECK_GE(val1, val2)
Definition: base/logging.h:702
BoolVar Not() const
Returns the logical negation of the current Boolean variable.
Definition: cp_model.h:80
::PROTOBUF_NAMESPACE_ID::RepeatedField< ::PROTOBUF_NAMESPACE_ID::int32 > * mutable_assumptions()
int64_t constant() const
Returns the constant term.
Definition: cp_model.h:302
void AddDecisionStrategy(absl::Span< const IntVar > variables, DecisionStrategyProto::VariableSelectionStrategy var_strategy, DecisionStrategyProto::DomainReductionStrategy domain_strategy)
Adds a decision strategy on a list of integer variables.
Definition: cp_model.cc:875
LinearExpr AddConstant(int64_t value) const
Adds a constant value to an integer variable and returns a linear expression.
Definition: cp_model.cc:100
Constraint AddAllDifferent(absl::Span< const IntVar > vars)
this constraint forces all variables to have different values.
Definition: cp_model.cc:631
Constraint AddEquality(const LinearExpr &left, const LinearExpr &right)
Adds left == right.
Definition: cp_model.cc:552
void add_vars(::PROTOBUF_NAMESPACE_ID::int32 value)
::operations_research::sat::CircuitConstraintProto * mutable_circuit()
TableConstraint AddAllowedAssignments(absl::Span< const IntVar > vars)
Adds an allowed assignments constraint.
Definition: cp_model.cc:670
void add_intervals(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8023
const std::string name
ReservoirConstraint AddReservoirConstraint(int64_t min_level, int64_t max_level)
Adds a reservoir constraint with optional refill/emptying events.
Definition: cp_model.cc:703
void add_demands(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8070
void AddTuple(absl::Span< const int64_t > tuple)
Adds a tuple of possible values to the constraint.
Definition: cp_model.cc:307
IntervalVar WithName(const std::string &name)
Sets the name of the variable.
Definition: cp_model.cc:361
::operations_research::sat::AutomatonConstraintProto * mutable_automaton()
::operations_research::sat::TableConstraintProto * mutable_table()
Constraint AddBoolOr(absl::Span< const BoolVar > literals)
Adds the constraint that at least one of the literals must be true.
Definition: cp_model.cc:511
Constraint AddProductEquality(IntVar target, absl::Span< const IntVar > vars)
Adds target == prod(vars).
Definition: cp_model.cc:816
void add_y_intervals(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:7932
IntervalVar NewFixedSizeIntervalVar(const LinearExpr &start, int64_t size)
Creates an interval variable with a fixed size.
Definition: cp_model.cc:475
LinearExpr & AddExpression(const LinearExpr &expr)
Adds another linear expression to the linear expression.
Definition: cp_model.cc:211
BoolVar GetBoolVarFromProtoIndex(int index)
Returns the Boolean variable from its index in the proto.
Definition: cp_model.cc:937
AutomatonConstraint AddAutomaton(absl::Span< const IntVar > transition_variables, int starting_state, absl::Span< const int > final_states)
An automaton constraint/.
Definition: cp_model.cc:711
::operations_research::sat::CumulativeConstraintProto * mutable_cumulative()
void add_vars(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:6961
Specialized circuit constraint.
Definition: cp_model.h:469
Constraint AddBoolXor(absl::Span< const BoolVar > literals)
Adds the constraint that a odd number of literal is true.
Definition: cp_model.cc:527
::operations_research::sat::NoOverlap2DConstraintProto * mutable_no_overlap_2d()
Specialized cumulative constraint.
Definition: cp_model.h:597
Specialized assignment constraint.
Definition: cp_model.h:515
int64_t coefficient
void AddDemand(IntervalVar interval, IntVar demand)
Adds a pair (interval, demand) to the constraint.
Definition: cp_model.cc:350
An integer variable.
Definition: cp_model.h:148
::operations_research::sat::IntegerVariableProto * add_variables()
int64_t tail
void Minimize(const LinearExpr &expr)
Adds a linear minimization objective.
Definition: cp_model.cc:846
void add_literals(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8440
const std::vector< int64_t > & coefficients() const
Returns the vector of coefficients.
Definition: cp_model.h:299
const std::string & name() const
Definition: cp_model.pb.h:9209
#define CHECK_LT(val1, val2)
Definition: base/logging.h:701
IntVar NewConstant(int64_t value)
Creates a constant variable.
Definition: cp_model.cc:457
PROTOBUF_ATTRIBUTE_REINITIALIZES void Clear() final
void Maximize(const LinearExpr &expr)
Adds a linear maximization objective.
Definition: cp_model.cc:857
LinearExpr & AddTerm(IntVar var, int64_t coeff)
Adds a term (var * coeff) to the linear expression.
Definition: cp_model.cc:198
::operations_research::sat::RoutesConstraintProto * mutable_routes()
IntVar GetIntVarFromProtoIndex(int index)
Returns the integer variable from its index in the proto.
Definition: cp_model.cc:953
IntervalVar NewIntervalVar(const LinearExpr &start, const LinearExpr &size, const LinearExpr &end)
Creates an interval variable from 3 affine expressions.
Definition: cp_model.cc:469
Constraint AddNotEqual(const LinearExpr &left, const LinearExpr &right)
Adds left != right.
Definition: cp_model.cc:619
::PROTOBUF_NAMESPACE_ID::int32 enforcement_literal(int index) const
Definition: cp_model.pb.h:9264
void ClearAssumptions()
Remove all assumptions from the model.
Definition: cp_model.cc:919
Constraint AddMaxEquality(IntVar target, absl::Span< const IntVar > vars)
Adds target == max(vars).
Definition: cp_model.cc:767
int64_t max
Definition: alldiff_cst.cc:140
void add_transition_head(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:9033
IntVar Var() const
Checks that the expression is 1 * var + 0, and returns var.
Definition: cp_model.cc:220
A Boolean variable.
Definition: cp_model.h:69
const ::operations_research::sat::IntegerVariableProto & variables(int index) const
CpModelProto proto
Constraint AddInverseConstraint(absl::Span< const IntVar > variables, absl::Span< const IntVar > inverse_variables)
An inverse constraint.
Definition: cp_model.cc:689
BoolVar ToBoolVar() const
Cast IntVar -> BoolVar.
Definition: cp_model.cc:90
MultipleCircuitConstraint AddMultipleCircuitConstraint()
Adds a multiple circuit constraint, aka the "VRP" (Vehicle Routing Problem) constraint.
Definition: cp_model.cc:666
void set_name(ArgT0 &&arg0, ArgT... args)
void add_times(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8201
void add_coeffs(::PROTOBUF_NAMESPACE_ID::int64 value)
int64_t SolutionIntegerMax(const CpSolverResponse &r, IntVar x)
Returns the max of an integer variable in a solution.
Definition: cp_model.cc:988
void add_transition_tail(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:8986
::PROTOBUF_NAMESPACE_ID::int64 solution_lower_bounds(int index) const
LinearExpr & AddVar(IntVar var)
Adds a single integer variable to the linear expression.
Definition: cp_model.cc:193
BoolVar PresenceBoolVar() const
Returns a BoolVar indicating the presence of this interval.
Definition: cp_model.cc:378
static LinearExpr ScalProd(absl::Span< const IntVar > vars, absl::Span< const int64_t > coeffs)
Constructs the scalar product of variables and coefficients.
Definition: cp_model.cc:154
int64_t SolutionIntegerMin(const CpSolverResponse &r, IntVar x)
Returns the min of an integer variable in a solution.
Definition: cp_model.cc:980
#define CHECK_LE(val1, val2)
Definition: base/logging.h:700
const ::operations_research::sat::ConstraintProto & constraints(int index) const
int64_t demand
Definition: resource.cc:125
::operations_research::sat::ConstraintProto * add_constraints()
int index() const
Returns the index of the variable in the model.
Definition: cp_model.h:193
void add_literals(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8585
bool ContainsKey(const Collection &collection, const Key &key)
Definition: map_util.h:200
bool SolutionBooleanValue(const CpSolverResponse &r, BoolVar x)
Evaluates the value of a Boolean literal in a solver response.
Definition: cp_model.cc:996
Constraint AddElement(IntVar index, absl::Span< const int64_t > values, IntVar target)
Adds the element constraint: values[index] == target.
Definition: cp_model.cc:650
IntervalVar GetIntervalVarFromProtoIndex(int index)
Returns the interval variable from its index in the proto.
Definition: cp_model.cc:959
const ::operations_research::sat::CpObjectiveProto & objective() const
const std::string & Name() const
Returns the name of the constraint (or the empty string if not set).
Definition: cp_model.cc:281
void add_domain(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:6788
std::string DebugString() const
Returns a debug string.
Definition: cp_model.cc:387
BoolVar Not(BoolVar x)
A convenient wrapper so we can write Not(x) instead of x.Not() which is sometimes clearer.
Definition: cp_model.cc:66
int64_t capacity
void AddEvent(IntVar time, int64_t demand)
Adds a mandatory event.
Definition: cp_model.cc:318
int index
Definition: pack.cc:509
IntVar NewIntVar(const Domain &domain)
Creates an integer variable with the given domain.
Definition: cp_model.cc:439
void add_transition_label(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:9080
Constraint AddMinEquality(IntVar target, absl::Span< const IntVar > vars)
Adds target == min(vars).
Definition: cp_model.cc:725
A dedicated container for linear expressions.
Definition: cp_model.h:250
Constraint OnlyEnforceIf(absl::Span< const BoolVar > literals)
The constraint will be enforced iff all literals listed here are true.
Definition: cp_model.cc:283
#define CHECK_EQ(val1, val2)
Definition: base/logging.h:698
static LinearExpr Sum(absl::Span< const IntVar > vars)
Constructs the sum of a list of variables.
Definition: cp_model.cc:146
void AddAssumptions(absl::Span< const BoolVar > literals)
Adds multiple literals to the model as assumptions.
Definition: cp_model.cc:913
Constraint(ConstraintProto *proto)
Definition: cp_model.cc:274
Constraint AddBoolAnd(absl::Span< const BoolVar > literals)
Adds the constraint that all literals must be true.
Definition: cp_model.cc:519
::operations_research::sat::DecisionStrategyProto * add_search_strategy()
::operations_research::sat::ConstraintProto * mutable_constraints(int index)
void AddOptionalEvent(IntVar time, int64_t demand, BoolVar is_active)
Adds a optional event.
Definition: cp_model.cc:325
CpModelProto const * model_proto
void AddArc(int tail, int head, BoolVar literal)
Add an arc to the circuit.
Definition: cp_model.cc:295
static LinearExpr BooleanScalProd(absl::Span< const BoolVar > vars, absl::Span< const int64_t > coeffs)
Constructs the scalar product of Booleans and coefficients.
Definition: cp_model.cc:178
void ClearHints()
Remove all hints.
Definition: cp_model.cc:905
void ScaleObjectiveBy(double scaling)
Sets scaling of the objective.
Definition: cp_model.cc:869
void add_x_intervals(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:7885
void add_values(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:8750
void set_name(ArgT0 &&arg0, ArgT... args)
We call domain any subset of Int64 = [kint64min, kint64max].
PROTOBUF_ATTRIBUTE_REINITIALIZES void Clear() final
Constraint AddLinMinEquality(const LinearExpr &target, absl::Span< const LinearExpr > exprs)
Adds target == min(exprs).
Definition: cp_model.cc:756
Specialized automaton constraint.
Definition: cp_model.h:563
::PROTOBUF_NAMESPACE_ID::int64 solution(int index) const
void add_tails(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8491
Constraint AddGreaterOrEqual(const LinearExpr &left, const LinearExpr &right)
Adds left >= right.
Definition: cp_model.cc:562
Constraint AddVariableElement(IntVar index, absl::Span< const IntVar > variables, IntVar target)
Adds the element constraint: variables[index] == target.
Definition: cp_model.cc:639
BoolVar WithName(const std::string &name)
Sets the name of the variable.
Definition: cp_model.cc:34
std::string DebugString() const
Debug string.
Definition: cp_model.cc:232
Constraint AddLessThan(const LinearExpr &left, const LinearExpr &right)
Adds left < right.
Definition: cp_model.cc:592
IntVar WithName(const std::string &name)
Sets the name of the variable.
Definition: cp_model.cc:80
BoolVar NewBoolVar()
Creates a Boolean variable.
Definition: cp_model.cc:449
Constraint AddNoOverlap(absl::Span< const IntervalVar > vars)
Adds a no-overlap constraint that ensures that all present intervals do not overlap in time.
Definition: cp_model.cc:826
void add_heads(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8538
Constraint WithName(const std::string &name)
Sets the name of the constraint.
Definition: cp_model.cc:276
void set_offset(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:7046
std::string DebugString() const
Returns a debug string.
Definition: cp_model.cc:104
void AddRectangle(IntervalVar x_coordinate, IntervalVar y_coordinate)
Adds a rectangle (parallel to the axis) to the constraint.
Definition: cp_model.cc:340
NoOverlap2DConstraint AddNoOverlap2D()
The no_overlap_2d constraint prevents a set of boxes from overlapping.
Definition: cp_model.cc:835
int64_t Value() const
Checks that the expression is constant and returns its value.
Definition: cp_model.cc:227
Collection of objects used to extend the Constraint Solver library.
void AddTransition(int tail, int head, int64_t transition_label)
Adds a transitions to the automaton.
Definition: cp_model.cc:333
TableConstraint AddForbiddenAssignments(absl::Span< const IntVar > vars)
Adds an forbidden assignments constraint.
Definition: cp_model.cc:679
::operations_research::sat::CpObjectiveProto * mutable_objective()
int64_t time
Definition: resource.cc:1691
This file implements a wrapper around the CP-SAT model proto.
absl::Span< const double > coefficients
::operations_research::sat::PartialVariableAssignment * mutable_solution_hint()
void AddHint(IntVar var, int64_t value)
Adds hinting to a variable.
Definition: cp_model.cc:899
IntervalVar NewOptionalIntervalVar(const LinearExpr &start, const LinearExpr &size, const LinearExpr &end, BoolVar presence)
Creates an optional interval variable from 3 affine expressions and a Boolean variable.
Definition: cp_model.cc:480
LinearExpr StartExpr() const
Returns the start linear expression.
Definition: cp_model.cc:366
bool RefIsPositive(int ref)
void add_coeffs(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:7008
LinearExpr SizeExpr() const
Returns the size linear expression.
Definition: cp_model.cc:370
std::ostream & operator<<(std::ostream &os, const BoolVar &var)
Definition: cp_model.cc:68
IntVar * var
Definition: expr_array.cc:1874
Constraint AddLessOrEqual(const LinearExpr &left, const LinearExpr &right)
Adds left <= right.
Definition: cp_model.cc:572
::operations_research::sat::ReservoirConstraintProto * mutable_reservoir()
void add_vars(::PROTOBUF_NAMESPACE_ID::int32 value)
::PROTOBUF_NAMESPACE_ID::int64 domain(int index) const
Definition: cp_model.pb.h:6777
CumulativeConstraint AddCumulative(IntVar capacity)
The cumulative constraint.
Definition: cp_model.cc:839
std::string Name() const
Returns the name of the interval (or the empty string if not set).
Definition: cp_model.cc:383
Constraint AddLinearConstraint(const LinearExpr &expr, const Domain &domain)
Adds expr in domain.
Definition: cp_model.cc:602
const IntervalConstraintProto & Proto() const
Returns the underlying protobuf object (useful for testing).
Definition: cp_model.h:385
void add_heads(::PROTOBUF_NAMESPACE_ID::int32 value)
Definition: cp_model.pb.h:8393
Wrapper class around the cp_model proto.
Definition: cp_model.h:617
const std::vector< IntVar > & variables() const
Returns the vector of variables.
Definition: cp_model.h:296
::operations_research::sat::IntegerVariableProto * mutable_variables(int index)
Constraint AddDivisionEquality(IntVar target, IntVar numerator, IntVar denominator)
Adds target = num / denom (integer division rounded towards 0).
Definition: cp_model.cc:788
Represents a Interval variable.
Definition: cp_model.h:341
int64_t value
Literal literal
Definition: optimization.cc:85
IntervalVar * interval
Definition: resource.cc:100
static LinearExpr BooleanSum(absl::Span< const BoolVar > vars)
Constructs the sum of a list of Booleans.
Definition: cp_model.cc:170
void add_values(::PROTOBUF_NAMESPACE_ID::int64 value)
const Constraint * ct
void CopyFrom(const CpModelProto &model_proto)
Replace the current model with the one from the given proto.
Definition: cp_model.cc:923
const IntegerVariableProto & Proto() const
Returns the underlying protobuf object (useful for testing).
Definition: cp_model.h:183
void add_demands(::PROTOBUF_NAMESPACE_ID::int64 value)
Definition: cp_model.pb.h:8248