def add_model_soc_constr( self, model: ScipModel, variables: List, rows: Iterator, A: dok_matrix, b: ndarray, ) -> Tuple: """Adds SOC constraint to the model using the data from mat and vec. Return tuple contains (QConstr, list of Constr, and list of variables). """ from pyscipopt.scip import quicksum # Assume first expression (i.e. t) is nonzero. expr_list = {i: [] for i in rows} for (i, j), c in A.items(): v = variables[j] try: expr_list[i].append((c, v)) except Exception: pass # Make a variable and equality constraint for each term. soc_vars = [] for i in rows: lb = 0 if len(soc_vars) == 0 else None var = model.addVar( obj=0, name="soc_t_%d" % i, vtype=VariableTypes.CONTINUOUS, lb=lb, ub=None, ) soc_vars.append(var) lin_expr_list = [ b[i] - quicksum(coeff * var for coeff, var in expr_list[i]) for i in rows ] new_lin_constrs = [ model.addCons(soc_vars[i] == lin_expr_list[i]) for i, _ in enumerate(lin_expr_list) ] # Interesting because only <=? t_term = soc_vars[0] * soc_vars[0] x_term = quicksum([var * var for var in soc_vars[1:]]) constraint = model.addCons(x_term <= t_term) return ( constraint, new_lin_constrs, soc_vars, )
def _solve( self, model: ScipModel, variables: List, constraints: List, data: Dict[str, Any], dims: Dict[str, Union[int, List]], ) -> Dict[str, Any]: """Solve and return a solution if one exists.""" solution = {} try: model.optimize() solution["value"] = model.getObjVal() sol = model.getBestSol() solution["primal"] = array([sol[v] for v in variables]) if not (data[s.BOOL_IDX] or data[s.INT_IDX]): # Not the following code calculating the dual values does not # always return the correct values, see tests `test_scip_lp_2` # and `test_scip_socp_1`. vals = [] # Get linear duals. for lc in constraints: if lc is not None and lc.isLinear(): dual = model.getDualsolLinear(lc) vals.append(dual) # Get non-linear duals. if len(dims[s.SOC_DIM]) > 1: for row in model.getNlRows(): vals.append(row.getDualsol()) solution["y"] = -array(vals) solution[s.EQ_DUAL] = solution["y"][0:dims[s.EQ_DIM]] solution[s.INEQ_DUAL] = solution["y"][dims[s.EQ_DIM]:] except Exception as e: log.warning("Error encountered when optimising %s: %s", model, e) solution[s.SOLVE_TIME] = model.getSolvingTime() solution['status'] = STATUS_MAP[model.getStatus()] if solution["status"] == s.SOLVER_ERROR and model.getNCountedSols( ) > 0: solution["status"] = s.OPTIMAL_INACCURATE return solution
def test_matrix(): m = SparseMatrix(Model("test"), ["hej", "med", "dig"], ["hello", "world"], "TEST") with pytest.raises(KeyError): m.make_var("hej", "dig") with pytest.raises(KeyError): m.make_var("hello", "world") m.make_var("med", "hello") m["med"]["hello"] str(m)
def _create_variables(self, model: ScipModel, data: Dict[str, Any], c: ndarray) -> List: """Create a list of variables.""" variables = [] for n, obj in enumerate(c): var_type = get_variable_type(n=n, data=data) variables.append( model.addVar( obj=obj, name="x_%d" % n, vtype=var_type, lb=None if var_type != VariableTypes.BINARY else 0, ub=None if var_type != VariableTypes.BINARY else 1, )) return variables
def solve_via_data( self, data: Dict[str, Any], warm_start: bool, verbose: bool, solver_opts: Dict[str, Any], solver_cache: Dict = None, ) -> Solution: """Returns the result of the call to the solver.""" from pyscipopt.scip import Model model = Model() A, b, c, dims = self._define_data(data) variables = self._create_variables(model, data, c) constraints = self._add_constraints(model, variables, A, b, dims) self._set_params(model, verbose, solver_opts) solution = self._solve(model, variables, constraints, data, dims) return solution
def add_model_lin_constr( self, model: ScipModel, variables: List, rows: Iterator, ctype: str, A: dok_matrix, b: ndarray, ) -> List: """Adds EQ/LEQ constraints to the model using the data from mat and vec. Return list contains constraints. """ from pyscipopt.scip import quicksum constraints = [] expr_list = {i: [] for i in rows} for (i, j), c in A.items(): v = variables[j] try: expr_list[i].append((c, v)) except Exception: pass for i in rows: # Ignore empty constraints. if expr_list[i]: expression = quicksum(coeff * var for coeff, var in expr_list[i]) constraint = model.addCons(( expression == b[i] ) if ctype == ConstraintTypes.EQUAL else (expression <= b[i])) constraints.append(constraint) else: constraints.append(None) return constraints
def __init__(self, name: str, x_keys: Iterable[str], y_keys: Iterable[str]): self.model = Model(name) self.X = SparseMatrix(self.model, x_keys, y_keys, "X") self.const: List[ExprCons] = list()
def _set_params( self, model: ScipModel, verbose: bool, solver_opts: Optional[Dict] = None, ) -> None: """Set model solve parameters.""" from pyscipopt import SCIP_PARAMSETTING # Default parameters: # These settings are needed to allow the dual to be calculated model.setPresolve(SCIP_PARAMSETTING.OFF) model.setHeuristics(SCIP_PARAMSETTING.OFF) model.disablePropagation() # Set model verbosity hide_output = not verbose model.hideOutput(hide_output) # General kwarg params scip_params = solver_opts.pop("scip_params", {}) if solver_opts: try: model.setParams(solver_opts) except KeyError as e: raise KeyError( "One or more solver params in {} are not valid: {}".format( list(solver_opts.keys()), e, )) # Scip specific params if scip_params: try: model.setParams(scip_params) except KeyError as e: raise KeyError( "One or more scip params in {} are not valid: {}".format( list(scip_params.keys()), e, ))
def is_optimized_mode(): s = Model() return is_memory_freed()
def test_not_freed(): if is_optimized_mode(): pytest.skip() m = Model() assert not is_memory_freed()