def read_cuts(self, path): """Read all cuts from csv files. csv files takes the form of: x.varName | y.varName | rhs a | b | c which specifies cut: alpha + ax + by >= c in minimization problem alpha + ax + by <= c in maximization problem Parameters ---------- path: string The location to read csv files """ self._update() for t in range(self.T - 1): m = self.models[t] if type(m) != list: coeffs = pandas.read_csv(path + "{}.csv".format(t), index_col=0).values for coeff in coeffs: m.addConstr( (m.alpha + gurobipy.LinExpr(coeff[:-1], m.states) - coeff[-1]) * m.modelsense >= 0) m.update() else: for k, m in enumerate(m): coeffs = pandas.read_csv(path + "{}_{}.csv".format(t, k), index_col=0).values for coeff in coeffs: m.addConstr( (m.alpha + gurobipy.LinExpr(coeff[:-1], m.states) - coeff[-1]) * m.modelsense >= 0) m.update()
def copy(self): # create a copy, gurobipy.LinExpr() attributes on each edge are not copied # If self has been optimized the copy may have a different optimal solution (of same obj value) cpy = AdExchange() cpy._model = self._model.copy() cpy._model.optimize() cpy._map = copy.copy(self._map) cpy._graph = networkx.DiGraph() copymorphism = { } #A map from vertices of self._graph to vertices of cpy._graph for v in self._graph.nodes(): cpy_v = copy.copy(v) copymorphism[v] = cpy_v cpy._graph.add_node( cpy_v, lin_constr=[gurobipy.LinExpr(), gurobipy.LinExpr()]) for e in self._graph.edges(): cpy_u = copymorphism[e[0]] cpy_v = copymorphism[e[1]] cpy._graph.add_edge( cpy_u, cpy_v, var=cpy._model.getVarByName(e[0].name + str(e[0].advertiser_id) + '->' + e[1].name + str(e[1].advertiser_id))) #if self._model.getAttr('Status') == 2: #if the self model has been optimized #cpy._model.optimize() return cpy
def MIP_minimize(Para, model, x_ecar, f_cost, ev_info): # 1. Pre-processing [ev_here, ev_wait, ev_pool] = ev_info # 2. Add objective # 1) charging income obj_reject = gp.LinExpr() for n in range(len(ev_pool)): var_select = x_ecar.select(n, '*', '*') var_coef = ev_pool[n, 4] * Para.Cost_charging obj_reject = obj_reject + var_coef * (1 - gp.quicksum(var_select)) # 2) charging park adjustment cost obj_adjust = gp.LinExpr() for n in range(len(ev_pool)): for p in range(Para.N_park): if n >= len(ev_here) and ev_pool[n, 5] != p: var_select = x_ecar.select(n, p, '*') var_coef = Para.Cost_adjust obj_adjust = obj_adjust + var_coef * gp.quicksum(var_select) # 3. Set objective objective = obj_reject + obj_adjust + gp.quicksum(f_cost) model.setObjective(objective, gp.GRB.MINIMIZE) return model
def _setup_dwell_time_constraints(self): print(" - Dwell time constraints ... ", end = "", flush = True) dt_sums = np.zeros((self._binapprox_p.n_t, self._binapprox_p.n_t)) for j in range(self._binapprox_p.n_t): dt_sums[j][j] = self._binapprox_p.dt[j] for k in range(j+1,self._binapprox_p.n_t): dt_sums[j][k] = dt_sums[j][k-1] + self._binapprox_p.dt[k] for i in range(self._binapprox_p.n_c): for k in range(1,self._binapprox_p.n_t): if dt_sums[0][k-1] < self._binapprox_p.min_up_times[i]: self._model.addLConstr(gp.LinExpr([1.0, -1.0], [self._b_bin_sym[(i,k)], \ self._b_bin_sym[(i,0)]]), gp.GRB.GREATER_EQUAL, 0.0) for j in range(1,self._binapprox_p.n_t): for k in range(j+1,self._binapprox_p.n_t): if dt_sums[j][k-1] < self._binapprox_p.min_up_times[i]: self._model.addLConstr(gp.LinExpr([1.0, -1.0, 1.0], [self._b_bin_sym[(i,k)], \ self._b_bin_sym[(i,j)], self._b_bin_sym[(i,j-1)]]), gp.GRB.GREATER_EQUAL, 0.0) if dt_sums[j][k-1] < self._binapprox_p.min_down_times[i]: self._model.addLConstr(gp.LinExpr([1.0, 1.0, -1.0], [self._b_bin_sym[(i,k)], \ self._b_bin_sym[(i,j-1)], self._b_bin_sym[(i,j)]]), gp.GRB.LESS_EQUAL, 1.0) print("done")
def add_constraints(lp_problem: LpProblem, model: gurobipy.Model) -> None: """ Add the constraints in a Flipy LpProblem to a gurobi model Parameters ---------- lp_problem: The Flipy object to grab the constraints from model: The gurobi model to add the constraints to """ for name, constraint in lp_problem.lp_constraints.items(): lhs_expr = [(coef, var.solver_var) for var, coef in constraint.lhs.expr.items()] if constraint.slack: lhs_expr += [((-1 if constraint.sense == 'leq' else 1), constraint.slack_variable.solver_var)] lhs_expr = gurobipy.LinExpr(lhs_expr) lhs_expr.addConstant(constraint.lhs.const) rhs_expr = gurobipy.LinExpr([ (coef, var.solver_var) for var, coef in constraint.rhs.expr.items() ]) rhs_expr.addConstant(constraint.rhs.const) if constraint.sense.lower() == 'leq': relation = gurobipy.GRB.LESS_EQUAL elif constraint.sense.lower() == 'geq': relation = gurobipy.GRB.GREATER_EQUAL else: relation = gurobipy.GRB.EQUAL constraint.solver_constraint = model.addConstr( lhs_expr, relation, rhs_expr, name) model.update()
def _create_constraints(self): """Creates the constraints""" model = self._model price_vars = self._price_vars # hourly bid surplus constraints bid_id_2_step_id_2_sbidvar = self._bid_id_2_step_id_2_sbidvar for bid_id, hourly_bid in self._dam_data.dam_bids.bid_id_2_hourly_bid.items( ): for step_id, step in hourly_bid.step_id_2_simple_bid.items(): expr = grb.LinExpr(0.0) svar = bid_id_2_step_id_2_sbidvar[bid_id][step_id] pi = price_vars[hourly_bid.period - 1] p = step[0] q = step[1] expr.addTerms([1, q], [svar, pi]) model.addConstr(expr, grb.GRB.GREATER_EQUAL, p * q, 'dual_' + str(bid_id) + '_' + str(step_id)) # block bid surplus constraints bid_id_2_bbidvar = self._bid_id_2_bbidvar for bid_id, block_bid in self._dam_data.dam_bids.bid_id_2_block_bid.items( ): expr = grb.LinExpr(0.0) s, l, m = bid_id_2_bbidvar[bid_id] p = block_bid.num_period * [block_bid.price] q = block_bid.num_period * [block_bid.quantity] pi = price_vars[block_bid.period - 1:block_bid.period + block_bid.num_period - 1] rhs = sum([i * j for i, j in zip(p, q)]) expr.addTerms([1, -1, 1], [s, l, m]) expr.addTerms(q, pi) model.addConstr(expr, grb.GRB.GREATER_EQUAL, rhs, 'dual_' + str(bid_id))
def add_bellman_constraint(self, curr_action_phi, next_action_phi, update=True, final_transition=False): lhs_coeffs = [(p, w) for w, p in zip(self.w, curr_action_phi) if abs(p) >= eps] lhs = grb.LinExpr(lhs_coeffs) if final_transition: rhs_coeffs = [] else: rhs_coeffs = [(self.gamma * p, w) for w, p in zip(self.w, next_action_phi) if abs(p) >= eps] yi_pos_var, yi_neg_var = self.add_yi() rhs_coeffs.append((1, yi_pos_var)) rhs_coeffs.append((-1, yi_neg_var)) rhs = grb.LinExpr(rhs_coeffs) rhs += self.action_reward if final_transition: rhs += self.goal_reward # w'*curr_phi == -1 + yi_pos - yi_neg + gammma * w'*next_phi self.model.addConstr(lhs == rhs) #store the constraint so we can store them to a file later if update: self.model.update()
def CreateConstraints(self): for i, item in enumerate(self.Items): binExpr = gp.LinExpr() for b, bin in enumerate(self.Bins): binExpr += self.ItemVariables[b][i] self.Model.addConstr(binExpr == 1) for b, bin in enumerate(self.Bins): """ for x in self.ItemVariables[b]: itemsInBin += x #itemsInBin.AddTerm(self.ItemVariables[b]) self.Model.addConstr(itemsInBin == 1) """ itemsInBin = gp.LinExpr() for i, item in enumerate(self.Items): #self.Model.addConstr(x * item.Weight <= bin.WeightLimit * self.BinVariables[b]) itemsInBin += self.ItemVariables[b][i] * item.Weight self.Model.addConstr( itemsInBin <= bin.WeightLimit * self.BinVariables[b]) # symmetry breaking, only valid if bins are homogeneous if b < len(self.Bins) - 1: self.Model.addConstr( self.BinVariables[b + 1] <= self.BinVariables[b]) # symmetry breaking for i, item in enumerate(self.Items): if b > i: self.Model.addConstr(self.ItemVariables[b][i] == 0)
def _run(self): self.model = gurobipy.Model("mb-deployment") for mb in self.mg.middleboxes: variableId = "mb_decision_{}".format(mb) self.mb_vars[mb] = self.model.addVar(lb=0.0, ub=1.0, obj=1.0, vtype=GRB.BINARY, name=variableId) for (mb, cp) in self.mg.edges: variableId = "mb_cp_assignment_{}_{}_{}".format(mb, self.scenario.requests[cp].tail, self.scenario.requests[cp].head) self.mb_assignment_vars[(mb,cp)] = self.model.addVar(lb=0.0, ub=1.0, obj=0.0, vtype=GRB.BINARY, name=variableId) self.model.update() self.model.setObjective(self.model.getObjective(), GRB.MINIMIZE) for cp in self.mg.communication_pairs: constr = gurobipy.LinExpr() for (mb,cp) in self.mg.edges_at_node[cp]: constr.addTerms(1.0, self.mb_assignment_vars[(mb,cp)]) self.model.addConstr(constr, GRB.EQUAL, 1.0, name="covering_{}_{}".format(self.scenario.requests[cp].tail, self.scenario.requests[cp].head)) for mb in self.mg.middleboxes: constr = gurobipy.LinExpr() for (mb,cp) in self.mg.edges_at_node[mb]: constr.addTerms(1.0, self.mb_assignment_vars[(mb,cp)]) constr.addTerms(-1.0 * self.scenario.middleboxes[mb], self.mb_vars[mb]) self.model.addConstr(constr, GRB.LESS_EQUAL, 0.0, name="upper_bound_{}".format(mb)) for (mb,cp) in self.mg.edges: constr = gurobipy.LinExpr() constr.addTerms(1.0, self.mb_assignment_vars[(mb,cp)]) constr.addTerms(-1.0, self.mb_vars[mb]) self.model.addConstr(constr, GRB.LESS_EQUAL, 0.0, name="lower_bound_{}_{}_{}".format(mb, self.scenario.requests[cp].tail, self.scenario.requests[cp].head)) self.model.update() self.model.setParam("Threads", 1) #self.model.write("fun.lp") self.model.optimize() self.status = GurobiStatus(status=self.model.getAttr("Status"), solCount=self.model.getAttr("SolCount"), objValue=self.model.getAttr("ObjVal"), objGap=self.model.getAttr("MIPGap"), objBound=self.model.getAttr("ObjBound"), integralSolution=True) if self.status.isFeasible(): for mb in self.mg.middleboxes: if self.mb_vars[mb].X > 0.5: self.mg.move_mb_to_active(mb) for (mb,cp) in self.mg.edges: if self.mb_assignment_vars[(mb,cp)].X > 0.5: self.mg.edge_in_matching.add((mb,cp)) self.mg.check_validity() return self.mg return None
def __init__(self, B, A=None, active_inds=[], c=None, primal=True, method='dual_simplex'): print('Building polyhedral model. Solve method: {}'.format(method)) self.model = gp.Model() self.primal = primal # add variables and constraints to the model self.m_B, self.n = B.shape if self.primal: self.x = [] self.y_pos = [] self.y_neg = [] for i in range(self.n): self.x.append( self.model.addVar(lb=-INF, ub=INF, name='x_{}'.format(i))) for i in range(self.m_B): self.y_pos.append( self.model.addVar(lb=0.0, ub=1.0, name='y_pos_{}'.format(i))) self.y_neg.append( self.model.addVar(lb=0.0, ub=1.0, name='y_neg_{}'.format(i))) self.model.addConstr(gp.LinExpr( list(B[i]) + [-1, 1], self.x + [self.y_pos[i], self.y_neg[i]]) == 0, name='B_{}'.format(i)) self.model.addConstr(gp.LinExpr([1] * (2 * self.m_B), self.y_pos + self.y_neg) == 1, name='1_norm') if A is not None: self.m_A = A.shape[0] for i in range(self.m_A): self.model.addConstr(gp.LinExpr(A[i], self.x) == 0, name='A_{}'.format(i)) else: self.m_A = 0 if c is not None: self.set_objective(c) self.set_active_inds(active_inds) self.set_method(method) else: raise RuntimeError('Not yet implemented') self.model.update() print('Polyhedral model built!')
def MIP_dispatch(Para, model, x_ecar, ev_info, sc_plan): # 1. Pre-processing [ev_here, ev_wait, ev_pool] = ev_info # 2. Add constraints # 1) maximum type of service for each EV for n in range(len(ev_pool)): var_select = x_ecar.select(n, '*', '*') if n < len(ev_here): model.addConstr(gp.quicksum(var_select) == 1) else: model.addConstr(gp.quicksum(var_select) <= 1) # 2) pre-defined limits of parking assignment for n in range(len(ev_here)): index_park = sc_plan[n, 1] var_select = x_ecar.select(n, index_park, '*') model.addConstr(gp.quicksum(var_select) == 1) # 3) will of parking adjustment for n in range(len(ev_pool)): if ev_pool[n, 6] == 0: index_park = ev_pool[n, 5] var_select = x_ecar.select(n, index_park, '*') model.addConstr(gp.quicksum(var_select) == 1) # 4) pre-defined limits of charging rate for n in range(len(ev_pool)): for k in range(Para.N_rate): if ev_pool[n, k + 7] == -1: var_select = x_ecar.select(n, '*', k) model.addConstr(gp.quicksum(var_select) == 0) # 5) charging station capacity for p in range(Para.N_park): expr = gp.LinExpr() for n in range(len(ev_pool)): var_select = x_ecar.select(n, p, '*') expr = expr + gp.quicksum(var_select) * ev_pool[n, 4] model.addConstr(expr <= np.sum(Para.Hour[:, p + 1])) # 6) adjustment limit if len(ev_here) > 0: expr = gp.LinExpr() for n in range(len(ev_here)): index_park = sc_plan[n, 1] index_rate = sc_plan[n, 2] expr = expr + x_ecar[n, index_park, index_rate] model.addConstr(expr >= len(ev_here) * 0.995) # 7) additional constraint if len(ev_pool) <= np.sum(Para.Park[:, 5]): model.addConstr(gp.quicksum(x_ecar) == len(ev_pool)) else: model.addConstr(gp.quicksum(x_ecar) >= np.sum(Para.Park[:, 5])) return model
def add_deadend_constraint(self, phi, yi_pos_var, update=True): lhs_coeffs = [(p, w) for w, p in zip(self.w, phi) if abs(p) >= eps] lhs = grb.LinExpr(lhs_coeffs) rhs_coeffs = [(1, yi_pos_var)] rhs = grb.LinExpr(rhs_coeffs) rhs += self.dead_end_value self.model.addConstr(lhs <= rhs) if update: self.model.update()
def initOptimisticProblemGrb(nS, nC, Q, S, R, q, r, U_lb, U_ub): """ Build the initial Gurobi model based on separating the control input U into positve and negative orthants. The separation creates 2^q problems to solve, q is the number of component of the control that can take both positve and negative values. """ global mModels, dictConstr, dictU mModels.clear() dictConstr.clear() dictU.clear() # Obtain the different partitions from the range of U listConstr = partitionRange(U_lb, U_ub) # Create the optimization problem variables counterPb = 0 for d in listConstr: # Create the gurobi model mOpt = gp.Model('Optimistic Model No' + str(counterPb)) # Variables of the sub problems are u and x_var u = [ mOpt.addVar(lb=-gp.GRB.INFINITY) for i in range(nC) ] x_var = [ mOpt.addVar(lb=-gp.GRB.INFINITY) for i in range(nS)] # Constraints on the variable x_var for i, xi in enumerate(x_var): coeffSup = [0 for l in range(nC)] coeffInf = [0 for l in range(nC)] dictConstr[(counterPb, i)] = \ (mOpt.addLConstr(gp.LinExpr(coeffSup + [-1], u + [xi]), gp.GRB.GREATER_EQUAL, 0), mOpt.addLConstr(gp.LinExpr(coeffInf + [-1], u + [xi]), gp.GRB.LESS_EQUAL, 0), mOpt.addLConstr(gp.LinExpr(coeffSup + [-1], u + [xi]), gp.GRB.GREATER_EQUAL, 0), mOpt.addLConstr(gp.LinExpr(coeffInf + [-1], u + [xi]), gp.GRB.LESS_EQUAL, 0), ) # For constraints on the control variable u for j, uj in enumerate(u): if d[j]: uj.lb = np.maximum(0, U_lb[j]) uj.ub = np.maximum(0, U_ub[j]) else: uj.lb = np.minimum(0, U_lb[j]) uj.ub = np.minimum(0, U_ub[j]) # When learning the dynamics, encode some that some components # of the control must be zero dictConstr[(counterPb,-j-1)] = \ mOpt.addLConstr(gp.LinExpr([0], [uj]), gp.GRB.EQUAL, 0) # Save the input and states variables dictU[counterPb] = (u, x_var, d) # Create the cost function for the current subproblems costVal = getQuadraticCost(x_var, u, Q, S, R, q, r) mOpt.setObjective(costVal) mModels[counterPb] = (mOpt, costVal) # Increment the counter variable counterPb = counterPb + 1
def addFlowConstrs(self): """ add commodity flow constraints """ num_nodes = self.num_nodes # edge flow variables edgeFlowVars = {} for i in xrange(1, num_nodes + 1): for j in xrange(1, num_nodes + 1): edgeFlowVars[i, j] = self.model.addVar(vtype=gp.GRB.INTEGER, name='f_%d_%d' % (i, j)) # dummy edge flow variables dummyEdgeFlowVars = {} for i in xrange(1, num_nodes + 1): dummyEdgeFlowVars[i] = self.model.addVar(vtype=gp.GRB.INTEGER, name='f_0_%d' % i) # integrate flow variables self.model.update() # ROOT node must send out 1 unit of flow for each node present self.model.addConstr( gp.quicksum(dummyEdgeFlowVars.values()) - gp.quicksum(self.nodeVars[i, 1] for i in xrange(1, num_nodes + 1)) == 0.0) # flow may only be sent over an edge if the edge is included in the solution # TODO: edge may exist only if flow is greater than zero for i in xrange(1, num_nodes + 1): for j in xrange(1, num_nodes + 1): self.model.addConstr( gp.LinExpr(self.edgeVars[i, j, 1] * num_nodes - edgeFlowVars[i, j]) >= 0.0) # self.model.addConstr(gp.LinExpr(edgeFlowVars[i,j] * num_nodes - self.edgeVars[i,j,1]) >= 0.0) for i in xrange(1, num_nodes + 1): self.model.addConstr( gp.LinExpr(self.dummyEdgeVars[i, 1] * num_nodes - dummyEdgeFlowVars[i]) >= 0.0) # self.model.addConstr(gp.LinExpr(dummyEdgeFlowVars[i] * num_nodes - self.dummyEdgeVars[i,1]) >= 0.0) # each node must consume exactly one unit of flow, if it is included in solution for i in xrange(1, num_nodes + 1): incoming = gp.quicksum( edgeFlowVars[src, i] for src in xrange(1, num_nodes + 1)) + dummyEdgeFlowVars[i] outgoing = gp.quicksum(edgeFlowVars[i, dst] for dst in xrange(1, num_nodes + 1)) self.model.addConstr(incoming - outgoing - self.nodeVars[i, 1] == 0) return
def create_mcf_model( substrate_topology , flows , new_flow_source_node , new_flow_destination_node , new_flow_tx_rate): mcf_model = gp.Model("mcf-model", gp.Env("gurobi.log")) new_flow = Flow( source_node = new_flow_source_node , destination_node = new_flow_destination_node , flow_tx_rate = new_flow_tx_rate , paths = None , splitting_ratio = None ) potential_flow_set = flows + [new_flow] link_set = {link_tuple: link_idx for link_idx, link_tuple in enumerate(substrate_topology.edges)} # F : flow_idx # -> source_node # -> destination_node # -> flow on link (source_node, destination_node) F = {(flow_idx, source_node, destination_node): mcf_model.addVar(name="F{%d,%d,%d}" % (flow_idx, source_node, destination_node)) for flow_idx, _ in enumerate(potential_flow_set) for source_node, destination_node in link_set.keys()} for flow_idx, flow in enumerate(potential_flow_set): for u in substrate_topology.nodes: egress_flow = gp.LinExpr(0.0) ingress_flow = gp.LinExpr(0.0) for v in substrate_topology.neighbors(u): egress_flow += F[flow_idx, u, v] ingress_flow += F[flow_idx, v, u] if u == flow.source_node: # forall adjacent nodes sum == -1 mcf_model.addConstr((egress_flow - ingress_flow) == 1.0) elif u == flow.destination_node: mcf_model.addConstr((ingress_flow - egress_flow) == 1.0) else: # forall adjacent nodes sum == 0 mcf_model.addConstr((ingress_flow - egress_flow) == 0.0) U = {link_index: gp.LinExpr(0.0) for link_index in link_set.values()} for (flow_idx, source_node, destination_node) in F.keys(): link_index = link_set[source_node, destination_node] U[link_index] += (F[flow_idx, source_node, destination_node] * potential_flow_set[flow_idx].flow_tx_rate) # U[link_index] += F[flow_idx, source_node, destination_node] alpha = mcf_model.addVar(name="alpha", lb=0.0, ub=1.0) for u, v in {tuple(sorted(t_i)) for t_i in link_set.keys()}: one_direction = link_set[u, v] other_direction = link_set[v, u] mcf_model.addConstr((U[one_direction] + U[other_direction]) <= LINK_CAPACITY * alpha) mcf_model.setObjective(alpha, gp.GRB.MINIMIZE) return mcf_model, U, F
def build_studies_constraint(self): """ Used to generate the study constraints (per study per house + 1) "sum of decisions variables of all students of a given study for a given house == 1 or more at extra cost" --> Soft constraint :return: """ for house in self.house_dataset.data: if house["room_count"] > 1: # --> Creating house entry in decision_variable_dict self.decision_variable_dict["Not_included"][ "Study_conditional"][house["ref"]] = {} # --> Creating list of study constraints corresponding to study for study in self.student_dataset.faculty_lst: # --> Creating and recording M decision variable for corresponding K out of N constraint self.decision_variable_dict["Not_included"]["Study_conditional"][house["ref"]][study] = \ self.model.addVar(vtype=GRB.BINARY, name="Study_conditional_" + study + "_" + str(house["ref"])) # --> Adding all decision variables (corresponding to given house) to constraint constraint = gp.LinExpr() for student in self.student_dataset.data: if student["study"] == study: constraint += self.decision_variable_dict["x"][ student["ref"]][house["ref"]] # --> Creating summation of student in house must have the same study constraint self.model.addConstr( constraint <= 0 + 1000 * self.decision_variable_dict["Not_included"] ["Study_conditional"][house["ref"]][study], "C_study_" + study + "_" + str(house["ref"])) # --> Creating K (= 1) out of N (= nb. of studies available) constraint constraint = self.recursive_add_to_linear_expression( self.decision_variable_dict["Not_included"] ["Study_conditional"][house["ref"]], gp.LinExpr()) # --> Creating and recording soft constraint variable self.decision_variable_dict["Included"]["Study_slack_x"][house["ref"]] = \ self.model.addVar(vtype=GRB.BINARY, name="Study_slack_x_" + str(house["ref"])) * (- 5) # All N_variables sum to nb faculties minus one lower constraint self.model.addConstr( constraint <= 1 - 1000 * self.decision_variable_dict["Included"] ["Study_slack_x"][house["ref"]], "C_study_K_of_N_lower_" + house["ref"]) return
def create_test_k_paths_model( target_topology , flows , new_source_node , new_destination_node , new_flow_tx_rate , k_disjoint_paths): path_allocation_model = gp.Model("path-allocation-model", gp.Env("gurobi.log")) new_flow = Flow( source_node = new_source_node , destination_node = new_destination_node , flow_tx_rate = new_flow_tx_rate , paths = k_disjoint_paths , splitting_ratio = None ) potential_flow_set = flows + [new_flow] X = {} for flow_index, flow in enumerate(potential_flow_set): flow_routing_constraint_variable = gp.LinExpr(0.0) for path_index, path in enumerate(flow.paths): X[flow_index, path_index] = path_allocation_model.addVar(name="X{%d,%d}" % (flow_index, path_index), lb=0.0, ub=1.0) flow_routing_constraint_variable += X[flow_index, path_index] path_allocation_model.addConstr(flow_routing_constraint_variable == 1.0) link_set = {tuple(sorted(link_tuple)): link_idx for link_idx, link_tuple in enumerate(target_topology.edges)} # Y: flow_index -> link_index -> portion of flow on link Y = {(flow_index, link_index): path_allocation_model.addVar(name="Y{%d,%d}" % (flow_index, link_index), lb=0.0, ub=1.0) for flow_index, flow in enumerate(potential_flow_set) for link_index in link_set.values()} Y_rhs = {(flow_index, link_index): gp.LinExpr(0.0) for flow_index, flow in enumerate(potential_flow_set) for link_index in link_set.values()} for flow_idnex, flow in enumerate(potential_flow_set): for path_index, path in enumerate(flow.paths): for link_tuple in nx.utils.pairwise(path): link_index = link_set[tuple(sorted(link_tuple))] Y_rhs[flow_index, link_index] += X[flow_index, path_index] * flow.flow_tx_rate for (flow_index, link_index), y_ik in Y_rhs.items(): path_allocation_model.addConstr(Y[flow_index, link_index] == y_ik) alpha = path_allocation_model.addVar("alpha", lb=0.0, ub=1.0) # U: link_index -> link_utilization U = {link_index: path_allocation_model.addVar(name="U{%s}" % str(link_index)) for link_index in link_set.values()} for (flow_index, link_index), y_ik in Y_rhs.items(): U[link_index] += y_ik for link_index, u_l in U.items(): path_allocation_model.addConstr(u_l <= (alpha * LINK_CAPACITY)) path_allocation_model.setObjective(alpha, gp.GRB.MINIMIZE) return path_allocation_model
def solve_fac_loc(xx, yy, subset, number_images, budget): model = gb.Model("k-center") x = {} y = {} z = {} for image_idx in range(number_images): # z_i: is a loss z[image_idx] = model.addVar(obj=1, ub=0.0, vtype="B", name="z_{}".format(image_idx)) m = len(xx) for node_idx in range(m): _x = xx[node_idx] _y = yy[node_idx] # y_i = 1 means i is facility, 0 means it is not if _y not in y: if _y in subset: y[_y] = model.addVar(obj=0, ub=1.0, lb=1.0, vtype="B", name="y_{}".format(_y)) else: y[_y] = model.addVar(obj=0, vtype="B", name="y_{}".format(_y)) # if not _x == _y: x[_x, _y] = model.addVar(obj=0, vtype="B", name="x_{},{}".format(_x, _y)) model.update() coef = [1 for j in range(number_images)] var = [y[j] for j in range(number_images)] model.addConstr(gb.LinExpr(coef, var), "=", rhs=budget + len(subset), name="k_center") yyy = {} for node_idx in range(m): _x = xx[node_idx] _y = yy[node_idx] if _x not in yyy: yyy[_x] = [] if _y not in yyy[_x]: yyy[_x].append(_y) # if not _x == _y: model.addConstr(x[_x, _y], "<", y[_y], name="Strong_{},{}".format(_x, _y)) for _x in yyy: coef = [] var = [] for _y in yyy[_x]: # if not _x==_y: coef.append(1) var.append(x[_x, _y]) coef.append(1) var.append(z[_x]) model.addConstr(gb.LinExpr(coef, var), "=", 1, name="Assign{}".format(_x)) model.__data = x, y, z return model
def _create_dual_feasibility_constraints(self): bid_id_2_step_id_2_sbidvar = self.bid_id_2_step_id_2_sbidvar bid_id_2_bbidvar = self.bid_id_2_bbidvar model = self.model period_2_pi = self.period_2_pi # step hourly bids for bid_id, hourly_bid in self.dam_data.dam_bids.bid_id_2_step_hourly_bid.items( ): for step_id, simple_bid in hourly_bid.step_id_2_simple_bid.items(): expr = grb.LinExpr(0.0) svar = bid_id_2_step_id_2_sbidvar[bid_id][step_id][1] pi = period_2_pi[hourly_bid.period] p = simple_bid.p q = simple_bid.q expr.addTerms([1, q], [svar, pi]) model.addConstr(expr, grb.GRB.GREATER_EQUAL, p * q, 'dual_' + str(bid_id) + '_' + str(step_id)) # piecewise hourly bids for bid_id, hourly_bid in self.dam_data.dam_bids.bid_id_2_piecewise_hourly_bid.items( ): for step_id, interpolated_bid in hourly_bid.step_id_2_interpolated_bid.items( ): expr = grb.LinExpr(0.0) pvar, svar = bid_id_2_step_id_2_sbidvar[bid_id][step_id] pi = period_2_pi[hourly_bid.period] p_start = interpolated_bid.p_start p_end = interpolated_bid.p_end q = interpolated_bid.q expr.addTerms([1, q, -(p_end - p_start) * q], [svar, pi, pvar]) model.addConstr(expr, grb.GRB.GREATER_EQUAL, p_start * q, 'dual_' + str(bid_id) + '_' + str(step_id)) # block bids bid_id_2_block_bid = self.dam_data.dam_bids.bid_id_2_block_bid block_bid_ids = self.dam_data.block_bid_constraints_bid_ids constraints = self.dam_data.block_bid_constraints_matrix u = self.block_bid_constraint_dual_vars for var_idx, bid_id in enumerate(block_bid_ids): block_bid = bid_id_2_block_bid[bid_id] expr = grb.LinExpr(0.0) y, s, l, m = bid_id_2_bbidvar[bid_id] p = [block_bid.price] * DamData.NUM_PERIODS q = block_bid.quantities pi = [period_2_pi[t + 1] for t in range(DamData.NUM_PERIODS)] rhs = sum([i * j for i, j in zip(p, q)]) expr.addTerms([1, -1, 1], [s, l, m]) expr.addTerms(q, pi) # add terms for the 'u' variables (dual vars of block bid constraints) coeffs = [con[var_idx] for con in constraints] expr.addTerms(coeffs, u) model.addConstr(expr, grb.GRB.GREATER_EQUAL, rhs, 'dual_' + str(bid_id))
def getObjective(self, node_weights, edge_weights): """ generate objective expression node_weights: (1,) -> 0.1, edge_weights: (1,2) -> 0.2 self.nodeVars: (1,) -> nodeVar, self.edgeVars: (1,2) -> edgeVar """ n_weights = [v for _, v in sorted(node_weights.iteritems())] n_vars = [v for _, v in sorted(self.nodeVars.iteritems())] e_weights = [v for _, v in sorted(edge_weights.iteritems())] e_vars = [v for _, v in sorted(self.edgeVars.iteritems())] # sum the weights of nodes and edges return gp.LinExpr(n_weights, n_vars) + gp.LinExpr(e_weights, e_vars)
def __init__(self, prob_type, dam_data, prob_name, working_dir): self.prob_type = prob_type self.dam_data = dam_data self.prob_name = prob_name self.model = grb.Model(prob_name) self.bid_id_2_step_id_2_sbidvar = {} self.bid_id_2_bbidvar = {} self.period_2_balance_con = {} self.period_2_pi = {} self.block_bid_constraint_dual_vars = [] self.loss_expr = grb.LinExpr(0.0) self.missed_surplus_expr = grb.LinExpr(0.0) self.surplus_expr = None self._working_dir = working_dir
def computePMR(x, y, evidence): ######################### ####### initialization du model #################### m = gp.Model("Pairwise Max Regret") m.setParam("OutputFlag", 0) ########################## ###### declaration des variables ########################## w = [] for i in range(len(x)): w.append(m.addVar(vtype=GRB.CONTINUOUS)) ########################### #### ajout des contraintes ########################### # cst : evidence for a, b in evidence: expr1 = gp.LinExpr() expr2 = gp.LinExpr() for i in range(len(w)): expr1.addTerms(a[i], w[i]) expr2.addTerms(b[i], w[i]) m.addConstr(expr1 >= expr2) # cst for i in range(len(w)): m.addConstr(w[i] >= 0) # cst : um (w[i],i=1..n) = 1 m.addConstr(gp.quicksum(w[i] for i in range(len(w))) <= 1) ######################### ###### def de l'objectif ########################## m.setObjective( gp.quicksum(w[i] * y[i] for i in range(len(w))) - gp.quicksum(w[i] * x[i] for i in range(len(w))), GRB.MAXIMIZE) #################### ######## resolution #################### m.optimize() obj = m.getObjective() return obj.getValue() # valeur trouver
def updateQ(self, s, a, o, s_prime, r): ''' Update this teams Q and V. ''' O = self.actions A = self.actions # Use linear programming to obtain optimal policy for this state try: # Create a new model m = grb.Model("MultiAgentMinimax") m.setParam("OutputFlag", 0) # Create variables pi = dict() for a in A: pi[a] = m.addVar(0.0, 1.0, vtype=grb.GRB.CONTINUOUS, name=str(a)) # Integrate new variables m.update() # Set objective m.setObjective( grb.LinExpr([(self.TeamQLearning.Q[s][(a, o)], pi[a]) for o in O for a in A]), grb.GRB.MAXIMIZE) # Add constraint: Sum_a pi(a) = 1 expr = grb.quicksum(m.getVars()) m.addConstr(expr == 1, "Total probability") # Add more constraints for o in O: expr = grb.LinExpr([(self.TeamQLearning.Q[s][(a, o)], pi[a]) for a in self.actions]) m.addConstr(expr >= 0) m.optimize() for a in A: self.TeamQLearning.policy[s][a] = pi[a].x except grb.GurobiError: print 'Error reported' # Update Q and V self.TeamQLearning.updateQ(s, a, o, s_prime, r)
def set_summarize_lprelax(U, S, T, w): """ Compute the summarization of T using S. """ sis = list(range(len(S))) i_si = defaultdict(list) for si, s in enumerate(S): for i in s: i_si[i].append(si) f = max(len(ss) for ss in i_si.values()) #print(i_si) m = grb.Model("set_summarize_ilp") # Add varaiables x_s = { si: m.addVar(lb=0, ub=1, vtype=grb.GRB.CONTINUOUS, name=f"x_{si}") for si in sis } y_s = { si: m.addVar(lb=0, ub=1, vtype=grb.GRB.CONTINUOUS, name=f"y_{si}") for si in sis } # Add constraints for i in T: expr = [(1, x_s[si]) for si in i_si[i]] expr = grb.LinExpr(expr) m.addConstr(expr >= 1, name=f"must_contain:{i}") expr = [(1, y_s[si]) for si in i_si[i]] expr = grb.LinExpr(expr) m.addConstr(expr == 0, name=f"must_not_exclude:{i}") for i in U - T: expr_part = [(1, y_s[si]) for si in i_si[i]] for si in i_si[i]: expr = expr_part + [(-1, x_s[si])] expr = grb.LinExpr(expr) m.addConstr(expr >= 0, name=f"exclude_if_included:{i}:{si}") # Add objective expr = [] expr.extend((1, x) for x in x_s.values()) expr.extend((1, y) for y in y_s.values()) expr = grb.LinExpr(expr) m.setObjective(expr, grb.GRB.MINIMIZE) return m, x_s, y_s, f
def extend_model_constraints(self, model): """ Extend the Gurobi model with the flow preservation constraints of the edge sub-LP. :param gurobipy.Model model: the Gurobi model """ req_name = self.dag_req.name.rsplit("_dag", 1)[0] for u in self.substrate_oriented.nodes: expr = [] # inflow for v in self.substrate_oriented.get_in_neighbors(u): if (v, u) in self.valid_edges: expr.append((-1.0, self.var_edge_flow[v, u])) if u in self.allowed_valid_nodes_i: expr.append((-1.0, self.var_node_flow_source[u])) # outflow for v in self.substrate_oriented.get_out_neighbors(u): if (u, v) in self.valid_edges: expr.append((1.0, self.var_edge_flow[u, v])) if u in self.allowed_valid_nodes_j: expr.append((1.0, self.var_node_flow_sink[u])) # create constraint for ij, u, commutativity index expr = gurobipy.LinExpr(expr) constr_name = construct_name("flow_preservation", req_name=req_name, vedge=self.ij, snode=u, comm_index=self.commutativity_index) model.addConstr(expr, gurobipy.GRB.EQUAL, 0.0, name=constr_name)
def add_model_lin_constr(self, model, variables, rows, ctype, mat, vec): """Adds EQ/LEQ constraints to the model using the data from mat and vec. Parameters ---------- model : GUROBI model The problem model. variables : list The problem variables. rows : range The rows to be constrained. ctype : GUROBI constraint type The type of constraint. mat : SciPy COO matrix The matrix representing the constraints. vec : NDArray The constant part of the constraints. Returns ------- list A list of constraints. """ import gurobipy as gp constr = [] for i in rows: start = mat.indptr[i] end = mat.indptr[i + 1] x = [variables[j] for j in mat.indices[start:end]] coeff = mat.data[start:end] expr = gp.LinExpr(coeff, x) constr.append(model.addLConstr(expr, ctype, vec[i])) return constr
def _add_cut_dual(self, rhs, gradient): if self.phi is None: self.phi = [None] * self.dual_n_samples self.phi = self._model.addVars(self.dual_n_samples, lb=self.bound, ub=gurobipy.GRB.INFINITY, obj=0.0, name='phi') #Add #scenario cuts temp = [None] * self.dual_n_samples for j in range(self.dual_n_samples): temp[j] = gurobipy.LinExpr( gradient, [find_states[j] for find_states in self.find_states]) # set up J self.alphas self.cuts.append( self._model.addConstrs(self.modelSense * (self.phi[j] - temp[j] - rhs) >= 0 for j in range(self.dual_n_samples))) self.cuts.append( self._model.addConstr(self.alpha - gurobipy.quicksum( #model sense [ self.dual_probability[i] * self.phi[i] for i in range(self.dual_n_samples) ]) <= 0)) self._model.update()
def add_qualifying_constraint(m, coefficients, M, K, N, thetaB, g_flag, t): ''' Add the qualifying constraints to model m. The qualifying constraint is formed by linearizing the Lagrangian with respect to x about x0. Then linearizing that with respect to theta about thetat. ''' qualifying_constraint = [] x = [[m.getVarByName("x_%d_%d" % (j, k)) for k in xrange(K)] for j in xrange(M)] for i in xrange(len(coefficients)): #calcuate the qualifying constraint formula g_expr = gb.LinExpr() g_expr.addConstant(coefficients[i][-1]) for j in xrange(M * K): g_expr.add(x[j / K][j % K] * coefficients[i][j]) qualifying_constraint.append(g_expr) #add the qualifying constraints if g_flag[i % K][i / K] != 0: ##################### Add constraints: g_expr ######################### if thetaB[i % K][i / K] == 1: m.addConstr(g_expr <= np.spacing(1), name="qc%d_%d_%d" % (t, k, i)) elif thetaB[i % K][i / K] == 0: m.addConstr(g_expr >= -np.spacing(1), name="qc%d_%d_%d" % (t, k, i)) m.update() #return qualifying constraints to calculate lagrange constraint return qualifying_constraint
def __iter__(self): exprs = [] # scalar if len(self.svecs): exprs.append( (gb.LinExpr(self.svals, vecs) for vecs in zip(*self.svecs))) # matrix if len(self.lvecs): def generate_matrix_rows(val, vec): for i in range(val.shape[0]): indptr = slice(val.indptr[i], val.indptr[i + 1]) yield gb.LinExpr(val.data[indptr], vec[val.indices[indptr]]) exprs += starmap(generate_matrix_rows, zip(self.lvals, self.lvecs)) # constant if iterable(self.cval): exprs.append(self.cval) elif self.cval != 0: exprs.append(repeat(self.cval)) return map(gb.quicksum, zip(*exprs))
def _create_constraints_track_node_loads(self): """ Create constraints to track the node loads. """ for req in self.requests: node_load_constr_dict = { node_res: [(-1.0, self.var_request_load[req][node_res])] for node_res in self.substrate.substrate_node_resources } for i in req.nodes: i_type = req.get_type(i) i_demand = req.get_node_demand(i) for u, var in self.var_aggregated_node_mapping[req][i].items(): node_res = i_type, u node_load_constr_dict[node_res].append((i_demand, var)) for node_res, expr in node_load_constr_dict.iteritems(): u_type, u = node_res constr_name = construct_name("track_node_load", req_name=req.name, snode=u, type=u_type) self.model.addConstr(gurobipy.LinExpr(expr), gurobipy.GRB.EQUAL, 0.0, name=constr_name)