55 #include "absl/status/status.h" 56 #include "absl/strings/match.h" 57 #include "absl/strings/str_format.h" 69 "Number of threads available for Gurobi.");
89 void Write(
const std::string& filename)
override;
93 void Reset()
override;
107 const MPVariable*
const variable,
double new_value,
108 double old_value)
override;
124 int64_t
nodes()
const override;
134 bool IsLP()
const override {
return !mip_; }
135 bool IsMIP()
const override {
return mip_; }
142 int major, minor, technical;
144 return absl::StrFormat(
"Gurobi library version %d.%d.%d\n", major, minor,
149 const absl::MutexLock lock(&hold_interruptions_mutex_);
158 LOG(DFATAL) <<
"ComputeExactConditionNumber not implemented for" 159 <<
" GUROBI_MIXED_INTEGER_PROGRAMMING";
164 LOG(DFATAL) <<
"ComputeExactConditionNumber not implemented for" 165 <<
" GUROBI_LINEAR_PROGRAMMING";
199 bool SetSolverSpecificParametersAsString(
202 void SetRelativeMipGap(
double value)
override;
203 void SetPrimalTolerance(
double value)
override;
204 void SetDualTolerance(
double value)
override;
205 void SetPresolveMode(
int value)
override;
206 void SetScalingMode(
int value)
override;
207 void SetLpAlgorithm(
int value)
override;
210 int gurobi_basis_status)
const;
212 int gurobi_basis_status,
int constraint_index)
const;
215 bool ModelIsNonincremental()
const;
217 void SetIntAttr(
const char*
name,
int value);
218 int GetIntAttr(
const char*
name)
const;
219 void SetDoubleAttr(
const char*
name,
double value);
220 double GetDoubleAttr(
const char*
name)
const;
222 int GetIntAttrElement(
const char*
name,
int index)
const;
223 void SetDoubleAttrElement(
const char*
name,
int index,
double value);
224 double GetDoubleAttrElement(
const char*
name,
int index)
const;
225 std::vector<double> GetDoubleAttrArray(
const char*
name,
int elements);
227 char GetCharAttrElement(
const char*
name,
int index)
const;
229 void CheckedGurobiCall(
int err)
const;
231 int SolutionCount()
const;
236 int current_solution_index_;
238 bool update_branching_priorities_ =
false;
244 std::vector<int> mp_var_to_gurobi_var_;
249 std::vector<int> mp_cons_to_gurobi_linear_cons_;
251 int num_gurobi_vars_ = 0;
254 int num_gurobi_linear_cons_ = 0;
256 bool had_nonincremental_change_ =
false;
261 mutable absl::Mutex hold_interruptions_mutex_;
266 void CheckedGurobiCall(
int err,
GRBenv*
const env) {
267 CHECK_EQ(0, err) <<
"Fatal error with code " << err <<
", due to " 272 struct GurobiInternalCallbackContext {
278 class GurobiMPCallbackContext :
public MPCallbackContext {
280 GurobiMPCallbackContext(
GRBenv* env,
281 const std::vector<int>* mp_var_to_gurobi_var,
282 int num_gurobi_vars,
bool might_add_cuts,
283 bool might_add_lazy_constraints);
287 bool CanQueryVariableValues()
override;
288 double VariableValue(
const MPVariable* variable)
override;
289 void AddCut(
const LinearRange& cutting_plane)
override;
290 void AddLazyConstraint(
const LinearRange& lazy_constraint)
override;
291 double SuggestSolution(
292 const absl::flat_hash_map<const MPVariable*, double>& solution)
override;
293 int64_t NumExploredNodes()
override;
297 void UpdateFromGurobiState(
298 const GurobiInternalCallbackContext& gurobi_internal_context);
304 template <
typename T>
306 const GurobiInternalCallbackContext& gurobi_internal_context,
308 void CheckedGurobiCall(
int gurobi_error_code)
const;
310 template <
typename GRBConstra
intFunction>
311 void AddGeneratedConstraint(
const LinearRange& linear_range,
312 GRBConstraintFunction grb_constraint_function);
315 const std::vector<int>*
const mp_var_to_gurobi_var_;
316 const int num_gurobi_vars_;
318 const bool might_add_cuts_;
319 const bool might_add_lazy_constraints_;
322 GurobiInternalCallbackContext current_gurobi_internal_callback_context_;
323 bool variable_values_extracted_ =
false;
324 std::vector<double> gurobi_variable_values_;
327 void GurobiMPCallbackContext::CheckedGurobiCall(
int gurobi_error_code)
const {
328 ::operations_research::CheckedGurobiCall(gurobi_error_code, env_);
331 GurobiMPCallbackContext::GurobiMPCallbackContext(
332 GRBenv* env,
const std::vector<int>* mp_var_to_gurobi_var,
333 int num_gurobi_vars,
bool might_add_cuts,
bool might_add_lazy_constraints)
336 num_gurobi_vars_(num_gurobi_vars),
337 might_add_cuts_(might_add_cuts),
338 might_add_lazy_constraints_(might_add_lazy_constraints) {}
340 void GurobiMPCallbackContext::UpdateFromGurobiState(
341 const GurobiInternalCallbackContext& gurobi_internal_context) {
342 current_gurobi_internal_callback_context_ = gurobi_internal_context;
343 variable_values_extracted_ =
false;
346 int64_t GurobiMPCallbackContext::NumExploredNodes() {
348 case MPCallbackEvent::kMipNode:
349 return static_cast<int64_t>(GurobiCallbackGet<double>(
351 case MPCallbackEvent::kMipSolution:
352 return static_cast<int64_t>(GurobiCallbackGet<double>(
355 LOG(
FATAL) <<
"Node count is supported only for callback events MIP_NODE " 356 "and MIP_SOL, but was requested at: " 361 template <
typename T>
362 T GurobiMPCallbackContext::GurobiCallbackGet(
363 const GurobiInternalCallbackContext& gurobi_internal_context,
364 const int callback_code) {
367 GRBcbget(gurobi_internal_context.gurobi_internal_callback_data,
368 gurobi_internal_context.where, callback_code,
369 static_cast<void*>(&result)));
374 switch (current_gurobi_internal_callback_context_.where) {
376 return MPCallbackEvent::kPolling;
378 return MPCallbackEvent::kPresolve;
380 return MPCallbackEvent::kSimplex;
382 return MPCallbackEvent::kMip;
384 return MPCallbackEvent::kMipSolution;
386 return MPCallbackEvent::kMipNode;
388 return MPCallbackEvent::kMessage;
390 return MPCallbackEvent::kBarrier;
396 << current_gurobi_internal_callback_context_.where;
397 return MPCallbackEvent::kUnknown;
401 bool GurobiMPCallbackContext::CanQueryVariableValues() {
403 if (
where == MPCallbackEvent::kMipSolution) {
406 if (
where == MPCallbackEvent::kMipNode) {
407 const int gurobi_node_status = GurobiCallbackGet<int>(
414 double GurobiMPCallbackContext::VariableValue(
const MPVariable* variable) {
415 CHECK(variable !=
nullptr);
416 if (!variable_values_extracted_) {
418 CHECK(
where == MPCallbackEvent::kMipSolution ||
419 where == MPCallbackEvent::kMipNode)
420 <<
"You can only call VariableValue at " 421 <<
ToString(MPCallbackEvent::kMipSolution) <<
" or " 422 <<
ToString(MPCallbackEvent::kMipNode)
424 const int gurobi_get_var_param =
where == MPCallbackEvent::kMipNode
428 gurobi_variable_values_.resize(num_gurobi_vars_);
430 current_gurobi_internal_callback_context_.gurobi_internal_callback_data,
431 current_gurobi_internal_callback_context_.where, gurobi_get_var_param,
432 static_cast<void*>(gurobi_variable_values_.data())));
433 variable_values_extracted_ =
true;
435 return gurobi_variable_values_[mp_var_to_gurobi_var_->at(variable->index())];
438 template <
typename GRBConstra
intFunction>
439 void GurobiMPCallbackContext::AddGeneratedConstraint(
440 const LinearRange& linear_range,
441 GRBConstraintFunction grb_constraint_function) {
442 std::vector<int> variable_indices;
443 std::vector<double> variable_coefficients;
444 const int num_terms = linear_range.linear_expr().terms().size();
445 variable_indices.reserve(num_terms);
446 variable_coefficients.reserve(num_terms);
447 for (
const auto& var_coef_pair : linear_range.linear_expr().terms()) {
448 variable_indices.push_back(
449 mp_var_to_gurobi_var_->at(var_coef_pair.first->index()));
450 variable_coefficients.push_back(var_coef_pair.second);
452 if (std::isfinite(linear_range.upper_bound())) {
453 CheckedGurobiCall(grb_constraint_function(
454 current_gurobi_internal_callback_context_.gurobi_internal_callback_data,
455 variable_indices.size(), variable_indices.data(),
457 linear_range.upper_bound()));
459 if (std::isfinite(linear_range.lower_bound())) {
460 CheckedGurobiCall(grb_constraint_function(
461 current_gurobi_internal_callback_context_.gurobi_internal_callback_data,
462 variable_indices.size(), variable_indices.data(),
464 linear_range.lower_bound()));
468 void GurobiMPCallbackContext::AddCut(
const LinearRange& cutting_plane) {
469 CHECK(might_add_cuts_);
472 <<
"Cuts can only be added at MIP_NODE, tried to add cut at: " 474 AddGeneratedConstraint(cutting_plane,
GRBcbcut);
477 void GurobiMPCallbackContext::AddLazyConstraint(
478 const LinearRange& lazy_constraint) {
479 CHECK(might_add_lazy_constraints_);
482 where == MPCallbackEvent::kMipSolution)
483 <<
"Lazy constraints can only be added at MIP_NODE or MIP_SOL, tried to " 484 "add lazy constraint at: " 486 AddGeneratedConstraint(lazy_constraint,
GRBcblazy);
489 double GurobiMPCallbackContext::SuggestSolution(
490 const absl::flat_hash_map<const MPVariable*, double>& solution) {
493 <<
"Feasible solutions can only be added at MIP_NODE, tried to add " 497 std::vector<double> full_solution(num_gurobi_vars_,
GRB_UNDEFINED);
498 for (
const auto& variable_value : solution) {
499 const MPVariable*
var = variable_value.first;
500 full_solution[mp_var_to_gurobi_var_->at(
var->index())] =
501 variable_value.second;
506 current_gurobi_internal_callback_context_.gurobi_internal_callback_data,
507 full_solution.data(), &objval));
512 struct MPCallbackWithGurobiContext {
521 void* raw_model_and_callback) {
522 MPCallbackWithGurobiContext*
const callback_with_context =
523 static_cast<MPCallbackWithGurobiContext*>(raw_model_and_callback);
524 CHECK(callback_with_context !=
nullptr);
525 CHECK(callback_with_context->context !=
nullptr);
526 CHECK(callback_with_context->callback !=
nullptr);
527 GurobiInternalCallbackContext gurobi_internal_context{
529 callback_with_context->context->UpdateFromGurobiState(
530 gurobi_internal_context);
531 callback_with_context->callback->RunCallback(callback_with_context->context);
537 void GurobiInterface::CheckedGurobiCall(
int err)
const {
538 ::operations_research::CheckedGurobiCall(err, env_);
541 void GurobiInterface::SetIntAttr(
const char*
name,
int value) {
545 int GurobiInterface::GetIntAttr(
const char*
name)
const {
551 void GurobiInterface::SetDoubleAttr(
const char*
name,
double value) {
555 double GurobiInterface::GetDoubleAttr(
const char*
name)
const {
561 void GurobiInterface::SetIntAttrElement(
const char*
name,
int index,
566 int GurobiInterface::GetIntAttrElement(
const char*
name,
int index)
const {
572 void GurobiInterface::SetDoubleAttrElement(
const char*
name,
int index,
576 double GurobiInterface::GetDoubleAttrElement(
const char*
name,
583 std::vector<double> GurobiInterface::GetDoubleAttrArray(
const char*
name,
585 std::vector<double> results(elements);
591 void GurobiInterface::SetCharAttrElement(
const char*
name,
int index,
595 char GurobiInterface::GetCharAttrElement(
const char*
name,
int index)
const {
602 GurobiInterface::GurobiInterface(
MPSolver*
const solver,
bool mip)
607 current_solution_index_(0) {
618 absl::GetFlag(FLAGS_num_gurobi_threads)));
630 const absl::MutexLock lock(&hold_interruptions_mutex_);
655 mp_var_to_gurobi_var_.clear();
656 mp_cons_to_gurobi_linear_cons_.clear();
657 num_gurobi_vars_ = 0;
658 num_gurobi_linear_cons_ = 0;
659 had_nonincremental_change_ =
false;
670 SetDoubleAttrElement(
GRB_DBL_ATTR_LB, mp_var_to_gurobi_var_.at(var_index),
672 SetDoubleAttrElement(
GRB_DBL_ATTR_UB, mp_var_to_gurobi_var_.at(var_index),
698 had_nonincremental_change_ =
true;
715 had_nonincremental_change_ =
true;
726 double new_value,
double old_value) {
731 int grb_var = mp_var_to_gurobi_var_.at(variable->
index());
732 int grb_cons = mp_cons_to_gurobi_linear_cons_.at(constraint->
index());
734 had_nonincremental_change_ =
true;
739 GRBchgcoeffs(model_, 1, &grb_cons, &grb_var, &new_value));
747 had_nonincremental_change_ =
true;
759 mp_var_to_gurobi_var_.at(variable->
index()),
768 if (!had_nonincremental_change_) {
777 if (!had_nonincremental_change_) {
779 for (
const auto& entry :
solver_->objective_->coefficients_) {
788 update_branching_priorities_ =
true;
797 return static_cast<int64_t>(iter);
805 LOG(DFATAL) <<
"Number of nodes only available for discrete problems.";
811 int gurobi_basis_status)
const {
812 switch (gurobi_basis_status) {
822 LOG(DFATAL) <<
"Unknown GRB basis status.";
828 int gurobi_basis_status,
int constraint_index)
const {
829 const int grb_index = mp_cons_to_gurobi_linear_cons_.at(constraint_index);
831 LOG(DFATAL) <<
"Basis status not available for nonlinear constraints.";
834 switch (gurobi_basis_status) {
839 double tolerance = 0.0;
844 VLOG(4) <<
"constraint " << constraint_index <<
" , slack = " << slack
845 <<
" , sense = " << sense;
846 if (fabs(slack) <= tolerance) {
867 LOG(DFATAL) <<
"Basis status only available after a solution has " 872 LOG(DFATAL) <<
"Basis status only available for continuous problems.";
875 const int grb_index = mp_cons_to_gurobi_linear_cons_.at(constraint_index);
877 LOG(DFATAL) <<
"Basis status not available for nonlinear constraints.";
880 const int gurobi_basis_status =
882 return TransformGRBConstraintBasisStatus(gurobi_basis_status,
890 LOG(DFATAL) <<
"Basis status only available after a solution has " 895 LOG(DFATAL) <<
"Basis status only available for continuous problems.";
898 const int grb_index = mp_var_to_gurobi_var_.at(variable_index);
899 const int gurobi_basis_status =
901 return TransformGRBVarBasisStatus(gurobi_basis_status);
906 const int total_num_vars =
solver_->variables_.size();
918 var->name().empty() ? nullptr :
var->name().c_str()));
919 mp_var_to_gurobi_var_.push_back(num_gurobi_vars_++);
923 std::vector<int> grb_cons_ind;
924 std::vector<int> grb_var_ind;
925 std::vector<double>
coef;
932 const int grb_ct_idx = mp_cons_to_gurobi_linear_cons_.at(
ct->index());
934 DCHECK(
ct->indicator_variable() ==
nullptr);
935 for (
const auto& entry :
ct->coefficients_) {
936 const int var_index = entry.first->index();
940 grb_cons_ind.push_back(grb_ct_idx);
941 grb_var_ind.push_back(mp_var_to_gurobi_var_.at(var_index));
942 coef.push_back(entry.second);
946 if (!grb_cons_ind.empty()) {
947 CheckedGurobiCall(
GRBchgcoeffs(model_, grb_cons_ind.size(),
948 grb_cons_ind.data(), grb_var_ind.data(),
957 int total_num_rows =
solver_->constraints_.size();
963 const int size =
ct->coefficients_.size();
964 std::vector<int> grb_vars;
965 std::vector<double> coefs;
966 grb_vars.reserve(size);
968 for (
const auto& entry :
ct->coefficients_) {
969 const int var_index = entry.first->index();
971 grb_vars.push_back(mp_var_to_gurobi_var_.at(var_index));
972 coefs.push_back(entry.second);
975 ct->name().empty() ? nullptr : const_cast<char*>(
ct->name().c_str());
976 if (
ct->indicator_variable() !=
nullptr) {
977 const int grb_ind_var =
978 mp_var_to_gurobi_var_.at(
ct->indicator_variable()->index());
979 if (
ct->lb() > -std::numeric_limits<double>::infinity()) {
981 model_,
name, grb_ind_var,
ct->indicator_value(), size,
982 grb_vars.data(), coefs.data(),
985 if (
ct->ub() < std::numeric_limits<double>::infinity() &&
986 ct->lb() !=
ct->ub()) {
988 model_,
name, grb_ind_var,
ct->indicator_value(), size,
991 mp_cons_to_gurobi_linear_cons_.push_back(-1);
995 if (
ct->lb() ==
ct->ub()) {
996 CheckedGurobiCall(
GRBaddconstr(model_, size, grb_vars.data(),
999 }
else if (
ct->lb() == -std::numeric_limits<double>::infinity()) {
1000 CheckedGurobiCall(
GRBaddconstr(model_, size, grb_vars.data(),
1003 }
else if (
ct->ub() == std::numeric_limits<double>::infinity()) {
1004 CheckedGurobiCall(
GRBaddconstr(model_, size, grb_vars.data(),
1009 coefs.data(),
ct->lb(),
ct->ub(),
1015 mp_cons_to_gurobi_linear_cons_.push_back(num_gurobi_linear_cons_++);
1037 bool GurobiInterface::SetSolverSpecificParametersAsString(
1042 void GurobiInterface::SetRelativeMipGap(
double value) {
1047 LOG(
WARNING) <<
"The relative MIP gap is only available " 1048 <<
"for discrete problems.";
1058 void GurobiInterface::SetPrimalTolerance(
double value) {
1069 void GurobiInterface::SetDualTolerance(
double value) {
1074 void GurobiInterface::SetPresolveMode(
int value) {
1093 void GurobiInterface::SetScalingMode(
int value) {
1113 void GurobiInterface::SetLpAlgorithm(
int value) {
1133 int GurobiInterface::SolutionCount()
const {
1137 bool GurobiInterface::ModelIsNonincremental()
const {
1139 if (c->indicator_variable() !=
nullptr) {
1152 ModelIsNonincremental() || had_nonincremental_change_) {
1163 VLOG(1) << absl::StrFormat(
"Model built in %s.",
1167 for (
const std::pair<const MPVariable*, double>& p :
1170 mp_var_to_gurobi_var_.at(p.first->index()), p.second);
1174 if (update_branching_priorities_) {
1177 mp_var_to_gurobi_var_.at(
var->index()),
1178 var->branching_priority());
1180 update_branching_priorities_ =
false;
1195 SetParameters(param);
1197 solver_->solver_specific_parameter_string_);
1199 std::unique_ptr<GurobiMPCallbackContext> gurobi_context;
1200 MPCallbackWithGurobiContext mp_callback_with_context;
1201 int gurobi_precrush = 0;
1202 int gurobi_lazy_constraint = 0;
1203 if (callback_ ==
nullptr) {
1206 gurobi_context = absl::make_unique<GurobiMPCallbackContext>(
1207 env_, &mp_var_to_gurobi_var_, num_gurobi_vars_,
1209 mp_callback_with_context.context = gurobi_context.get();
1210 mp_callback_with_context.callback = callback_;
1212 model_, CallbackImpl, static_cast<void*>(&mp_callback_with_context)));
1228 VLOG(1) << absl::StrFormat(
"Solved in %s.",
1234 VLOG(1) << absl::StrFormat(
"Solution status %d.\n", optimization_status);
1235 const int solution_count = SolutionCount();
1237 switch (optimization_status) {
1253 if (solution_count > 0) {
1267 <<
"Best objective bound is not available, error=" << error
1274 current_solution_index_ = 0;
1280 const std::vector<double> grb_variable_values =
1282 for (
int i = 0; i <
solver_->variables_.size(); ++i) {
1284 const double val = grb_variable_values.at(mp_var_to_gurobi_var_.at(i));
1285 var->set_solution_value(val);
1286 VLOG(3) <<
var->name() <<
", value = " << val;
1291 const std::vector<double> grb_reduced_costs =
1293 for (
int i = 0; i <
solver_->variables_.size(); ++i) {
1295 const double rc = grb_reduced_costs.at(mp_var_to_gurobi_var_.at(i));
1296 var->set_reduced_cost(rc);
1297 VLOG(4) <<
var->name() <<
", reduced cost = " << rc;
1302 std::vector<double> grb_dual_values =
1304 for (
int i = 0; i <
solver_->constraints_.size(); ++i) {
1306 const double dual_value =
1307 grb_dual_values.at(mp_cons_to_gurobi_linear_cons_.at(i));
1308 ct->set_dual_value(dual_value);
1309 VLOG(4) <<
"row " <<
ct->index() <<
", dual value = " << dual_value;
1325 if (status_or.ok())
return status_or.value();
1328 if (absl::IsUnimplemented(status_or.status()))
return absl::nullopt;
1331 LOG(
INFO) <<
"Invalid Gurobi status: " << status_or.status();
1335 response.set_status_str(status_or.status().ToString());
1341 if (!mip_)
return false;
1348 if (current_solution_index_ + 1 >= SolutionCount()) {
1351 current_solution_index_++;
1357 const std::vector<double> grb_variable_values =
1360 for (
int i = 0; i <
solver_->variables_.size(); ++i) {
1362 var->set_solution_value(
1363 grb_variable_values.at(mp_var_to_gurobi_var_.at(i)));
1377 VLOG(1) <<
"Writing Gurobi model file \"" << filename <<
"\".";
1378 const int status =
GRBwrite(model_, filename.c_str());
1389 callback_ = mp_callback;
MPSolverInterface * BuildGurobiInterface(bool mip, MPSolver *const solver)
std::function< const char *(GRBenv *env)> GRBgeterrormsg
#define GRB_INT_PAR_PRECRUSH
ResultStatus
The status of solving the problem.
std::function< int(GRBmodel *model, const char *attrname, int element, double *valueP)> GRBgetdblattrelement
#define GRB_METHOD_PRIMAL
void set_variable_as_extracted(int var_index, bool extracted)
Advanced usage: incrementality from one solve to the next.
void AddVariable(MPVariable *const var) override
#define GRB_INT_PAR_OUTPUTFLAG
#define GRB_INT_ATTR_NUMVARS
#define GRB_GREATER_EQUAL
bool SupportsCallbacks() const override
double best_objective_bound_
const std::vector< MPConstraint * > & constraints() const
Returns the array of constraints handled by the MPSolver.
std::string SolverVersion() const override
#define GRB_CHAR_ATTR_VTYPE
void set_constraint_as_extracted(int ct_index, bool extracted)
void BranchingPriorityChangedForVariable(int var_index) override
std::function< int(GRBmodel *model, const char *attrname, int *valueP)> GRBgetintattr
#define GRB_DBL_ATTR_NODECOUNT
int64_t nodes() const override
std::function< int(GRBmodel *model, const char *filename)> GRBwrite
SynchronizationStatus sync_status_
#define GRB_DBL_PAR_INTFEASTOL
#define GRB_INT_ATTR_CBASIS
std::function< int(GRBenv *env, const char *paramname, double value)> GRBsetdblparam
#define VLOG(verboselevel)
const MPObjective & Objective() const
Returns the objective object.
void ExtractNewConstraints() override
#define GRB_INT_ATTR_VBASIS
A C++ wrapper that provides a simple and unified interface to several linear programming and mixed in...
void SetVariableBounds(int var_index, double lb, double ub) override
absl::optional< MPSolutionResponse > DirectlySolveProto(const MPModelRequest &request) override
std::function< GRBenv *(GRBmodel *model)> GRBgetenv
absl::StatusOr< GRBenv * > GetGurobiEnv()
struct _GRBmodel GRBmodel
std::function< int(void *cbdata, int lazylen, const int *lazyind, const double *lazyval, char lazysense, double lazyrhs)> GRBcblazy
const absl::string_view ToString(MPSolver::OptimizationProblemType optimization_problem_type)
#define GRB_DBL_PAR_OBJSCALE
std::function< int(GRBmodel *model, const char *attrname, int element, char newvalue)> GRBsetcharattrelement
void SetObjectiveCoefficient(const MPVariable *const variable, double coefficient) override
std::function< int(GRBenv *env, GRBmodel **modelP, const char *Pname, int numvars, double *obj, double *lb, double *ub, char *vtype, char **varnames)> GRBnewmodel
void AddRowConstraint(MPConstraint *const ct) override
Advanced usage: presolve mode.
BasisStatus
Advanced usage: possible basis status values for a variable and the slack variable of a linear constr...
void ExtractNewVariables() override
std::function< int(GRBenv *env, const char *paramname, int value)> GRBsetintparam
bool InterruptSolve() override
MPSolver::ResultStatus result_status_
#define GRB_CHAR_ATTR_SENSE
#define GRB_DBL_PAR_MIPGAP
void * gurobi_internal_callback_data
int64_t iterations() const override
GurobiInterface(MPSolver *const solver, bool mip)
~GurobiInterface() override
int GetIntegerParam(MPSolverParameters::IntegerParam param) const
Returns the value of an integer parameter.
std::function< int(GRBmodel *model)> GRBfreemodel
std::function< int(GRBmodel *model, int numnz, int *vind, double *vval, double obj, double lb, double ub, char vtype, const char *varname)> GRBaddvar
#define GRB_CB_MIPNODE_NODCNT
#define GRB_CB_MIPSOL_NODCNT
void * underlying_solver() override
The class for variables of a Mathematical Programming (MP) model.
std::function< int(GRBenv *env)> GRBresetparams
#define GRB_INT_ATTR_STATUS
void ExtractObjective() override
#define GRB_DBL_ATTR_SLACK
std::function< int(GRBmodel *model, const char *attrname, double *valueP)> GRBgetdblattr
bool SetSolverSpecificParametersAsString(const std::string ¶meters)
Advanced usage: pass solver specific parameters in text format.
ABSL_FLAG(int, num_gurobi_threads, 4, "Number of threads available for Gurobi.")
bool NextSolution() override
#define GRB_DBL_PAR_OPTIMALITYTOL
std::function< int(void *cbdata, const double *solution, double *objvalP)> GRBcbsolution
friend class MPConstraint
#define GRB_INT_PAR_SOLUTIONNUMBER
std::function< int(void *cbdata, int cutlen, const int *cutind, const double *cutval, char cutsense, double cutrhs)> GRBcbcut
void SetConstraintBounds(int row_index, double lb, double ub) override
std::function< int(GRBmodel *model, int cnt, int *cind, int *vind, double *val)> GRBchgcoeffs
#define GRB_DBL_ATTR_OBJVAL
std::function< int(GRBmodel *model, const char *attrname, int element, int newvalue)> GRBsetintattrelement
#define GRB_INT_PAR_SCALEFLAG
void SetCallback(MPCallback *mp_callback) override
std::function< int(void *cbdata, int where, int what, void *resultP)> GRBcbget
void ClearConstraint(MPConstraint *const constraint) override
std::function< void(GRBmodel *model)> GRBterminate
#define GRB_DBL_PAR_TIMELIMIT
std::function< int(GRBmodel *lp, const char *name, int binvar, int binval, int nvars, const int *vars, const double *vals, char sense, double rhs)> GRBaddgenconstrIndicator
virtual void SetIntegerParamToUnsupportedValue(MPSolverParameters::IntegerParam param, int value)
std::function< int(GRBmodel *model, int(GUROBI_STDCALL *cb)(CB_ARGS), void *usrdata)> GRBsetcallbackfunc
#define GRB_DBL_PAR_FEASIBILITYTOL
#define GRB_DBL_ATTR_START
std::function< int(GRBmodel *model, const char *attrname, int element, double newvalue)> GRBsetdblattrelement
std::function< int(GRBmodel *model)> GRBupdatemodel
bool IsMIP() const override
void SetCommonParameters(const MPSolverParameters ¶m)
int64_t time_limit() const
static constexpr int64_t kUnknownNumberOfIterations
std::function< int(GRBenv *dest, GRBenv *src)> GRBcopyparams
The class for constraints of a Mathematical Programming (MP) model.
feasible, or stopped by limit.
std::function< int(GRBmodel *model, const char *attrname, double newvalue)> GRBsetdblattr
#define DCHECK_GE(val1, val2)
void SetMIPParameters(const MPSolverParameters ¶m)
SharedResponseManager * response
#define GRB_NONBASIC_UPPER
#define GRB_DBL_ATTR_OBJCON
bool IsContinuous() const override
#define GRB_INT_PAR_PRESOLVE
#define CHECK_EQ(val1, val2)
bool constraint_is_extracted(int ct_index) const
std::function< int(GRBmodel *model, const char *attrname, int element, char *valueP)> GRBgetcharattrelement
void InvalidateSolutionSynchronization()
#define GRB_INT_PAR_METHOD
#define GRB_INT_ATTR_SOLCOUNT
int index() const
Returns the index of the constraint in the MPSolver::constraints_.
#define GRB_INT_ATTR_MODELSENSE
#define GRB_CB_MIPNODE_STATUS
absl::Status SetSolverSpecificParameters(const std::string ¶meters, GRBenv *gurobi)
#define LOG_IF(severity, condition)
#define GRB_DBL_ATTR_OBJBOUND
#define DCHECK(condition)
int last_constraint_index_
int index() const
Returns the index of the variable in the MPSolver::variables_.
double ComputeExactConditionNumber() const override
absl::Duration GetDuration() const
void SetObjectiveOffset(double value) override
#define GRB_INT_ATTR_BRANCHPRIORITY
std::function< int(GRBmodel *model)> GRBoptimize
#define GRB_CB_MIPSOL_SOL
bool CheckSolutionIsSynchronized() const
void SetOptimizationDirection(bool maximize) override
static constexpr int64_t kUnknownNumberOfNodes
#define DCHECK_EQ(val1, val2)
#define GRB_DBL_ATTR_POOLOBJVAL
bool CheckSolutionIsSynchronizedAndExists() const
void Write(const std::string &filename) override
void ClearObjective() override
#define GRB_INT_PAR_LAZYCONSTRAINTS
#define LOG_FIRST_N(severity, n)
void SetVariableInteger(int var_index, bool integer) override
std::function< int(GRBmodel *model, const char *attrname, int element, int *valueP)> GRBgetintattrelement
std::function< int(GRBmodel *model, const char *attrname, int newvalue)> GRBsetintattr
std::function< void(GRBenv *env)> GRBfreeenv
std::function< int(GRBmodel *model, int numnz, int *cind, double *cval, char sense, double rhs, const char *constrname)> GRBaddconstr
void SetCoefficient(MPConstraint *const constraint, const MPVariable *const variable, double new_value, double old_value) override
This mathematical programming (MP) solver class is the main class though which users build and solve ...
Collection of objects used to extend the Constraint Solver library.
bool IsLP() const override
Start solve from scratch.
#define GRB_METHOD_BARRIER
bool might_add_cuts() const
MPSolver::BasisStatus row_status(int constraint_index) const override
#define GRB_INT_PAR_THREADS
This class stores parameter settings for LP and MIP solvers.
#define GRB_DBL_ATTR_ITERCOUNT
Algorithm to solve linear programs.
MPSolver::BasisStatus column_status(int variable_index) const override
#define GRB_CB_MIPNODE_REL
void ResetExtractionInformation()
bool might_add_lazy_constraints() const
GurobiMPCallbackContext * context
bool enable_internal_solver_output() const
std::function< void(int *majorP, int *minorP, int *technicalP)> GRBversion
MPSolver::ResultStatus Solve(const MPSolverParameters ¶m) override
bool AddIndicatorConstraint(MPConstraint *const ct) override
std::function< int(GRBenv *env, const char *paramname, double *valueP)> GRBgetdblparam
absl::StatusOr< MPSolutionResponse > GurobiSolveProto(const MPModelRequest &request, GRBenv *gurobi_env)
double offset() const
Gets the constant term in the objective.
#define GRB_INT_ATTR_NUMCONSTRS
double time_limit_in_secs() const
bool variable_is_extracted(int var_index) const
#define GRB_NONBASIC_LOWER
std::function< int(GRBmodel *model, const char *attrname, int first, int len, double *values)> GRBgetdblattrarray
std::function< int(GRBmodel *model, int numnz, int *cind, double *cval, double lower, double upper, const char *constrname)> GRBaddrangeconstr