def formulate(module_name): m = ilib.import_module(module_name) prob = DipProblem() arc_vars = LpVariable.dicts("UseArc", m.ARCS, 0, 1, LpBinary) # objective prob += lpSum(m.ARC_COSTS[x] * arc_vars[x] for x in m.ARCS) # degree constraints for city in m.CITIES: prob += lpSum(arc_vars[x] for x in m.CITY_ARCS[city]) \ == 2 # dictionary for symmetric arcs, can be # accessed using (i, j) and (j, i) symmetric = {} for i in m.CITIES: for j in m.CITIES: if i < j: symmetric[(i, j)] = (i, j) symmetric[(j, i)] = (i, j) prob.CITIES = m.CITIES prob.symmetric = symmetric prob.arc_vars = arc_vars return prob
def formulate(module_name): m = ilib.import_module(module_name) lines = m.gap_data.splitlines() line = lines[1].split() #first line is blank NUM_MACHINES = int(line[0]) NUM_TASKS = int(line[1]) MACHINES = list(range(NUM_MACHINES)) TASKS = list(range(NUM_TASKS)) MACHINES_TASKS = [(m, t) for m in MACHINES for t in TASKS] COSTS = [] line_num = 2 for m in MACHINES: line = lines[line_num].split() assert len(line) == NUM_TASKS COSTS.append([int(f) for f in line]) line_num += 1 RESOURCE_USE = [] for m in MACHINES: line = lines[line_num].split() assert len(line) == NUM_TASKS RESOURCE_USE.append([int(f) for f in line]) line_num += 1 line = lines[line_num].split() assert len(line) == NUM_MACHINES CAPACITIES = [int(f) for f in line] assignVars = [] for m in MACHINES: v = [] for t in TASKS: v.append(LpVariable("M%dT%d" % (m, t), cat=LpBinary)) assignVars.append(v) prob = DipProblem("GAP") # objective prob += lpSum(assignVars[m][t] * COSTS[m][t] for m, t in MACHINES_TASKS), "min" # machine capacity (knapsacks, relaxation) for m in MACHINES: prob.relaxation[m] += lpSum(assignVars[m][t] * RESOURCE_USE[m][t] for t in TASKS) <= CAPACITIES[m] # assignment for t in TASKS: prob += lpSum(assignVars[m][t] for m in MACHINES) == 1 prob.assignVars = assignVars prob.MACHINES = MACHINES prob.TASKS = TASKS return prob
def formulate(cp): prob = DipProblem("Coke", display_mode='xdot', display_interval=None) # create variables LOC_SIZES = [(l, s) for l in cp.LOCATIONS for s in cp.SIZES] buildVars = LpVariable.dicts("Build", LOC_SIZES, cat=LpBinary) # create arcs flowVars = LpVariable.dicts("Arcs", cp.ARCS) BIG_M = max(sum(cp.supply.values()), sum(cp.demand.values())) for a in cp.ARCS: flowVars[a].bounds(0, BIG_M) # objective prob += 1e6 * lpSum(buildVars[(l, s)] * cp.build_costs[s] \ for (l, s) in LOC_SIZES) + \ lpSum(flowVars[(s, d)] * cp.transport_costs[(s, d)] \ for (s, d) in cp.ARCS), "min" # plant availability - assumes that SIZES are numeric, # which they should be for loc in cp.LOCATIONS: prob += lpSum(flowVars[(loc, i)] for i in cp.CUSTOMERS) \ <= lpSum(buildVars[(loc, s)] * s for s in cp.SIZES) # one size for loc in cp.LOCATIONS: prob += lpSum(buildVars[(loc, s)] for s in cp.SIZES) == 1 # conserve flow (mines) # flows are in terms of tonnes of coke for m in cp.MINES: prob += lpSum(flowVars[(m, j)] for j in cp.LOCATIONS) \ <= cp.supply[m] # conserve flow (locations) # convert from coal to coke for loc in cp.LOCATIONS: prob += lpSum(flowVars[(m, loc)] for m in cp.MINES) - \ cp.conversion_factor * \ lpSum(flowVars[(loc, c)] for c in cp.CUSTOMERS) \ >= 0 for c in cp.CUSTOMERS: prob += lpSum(flowVars[(loc, c)] for loc in cp.LOCATIONS) \ >= cp.demand[c] prob.cp = cp prob.buildVars = buildVars prob.flowVars = flowVars return prob
def Solver(args): global x, y prob = DipProblem("CVPMP", display_mode=display_mode, layout='dot', display_interval=0) X = [(i, j) for i in V for j in V] x = LpVariable.dicts("x", X, 0, 1, LpBinary) y = LpVariable.dicts("y", V, 0, 1, LpBinary) prob += (lpSum(d[i, j] * x[(i, j)] for i in V for j in V), "min") #linking constraints for j in V: prob += lpSum(x[(i, j)] for i in V) == 1 #non-relaxing for i in V: prob.relaxation[i] += lpSum(w[j] * x[(i, j)] for j in V) <= s[i] * y[i] prob += lpSum(y[i] for i in V) == p if args.useCustomSolver: prob.relaxed_solver = solve_subproblem dippyOpts = addDippyOpts(args) Solve(prob, dippyOpts) #Make solution solution = [] for i in V: if y[i].varValue: cluster = [] for j in V: if x[(i, j)].varValue: cluster.append(j) solution.append((i, cluster)) return round(prob.objective.value()), solution
def formulate(bpp, args): prob = DipProblem("Bin Packing") assign_vars = LpVariable.dicts("x", [(i, j) for i in bpp.BINS for j in bpp.ITEMS], cat=LpBinary) use_vars = LpVariable.dicts("y", bpp.BINS, cat=LpBinary) waste_vars = LpVariable.dicts("w", bpp.BINS, 0, None) prob += lpSum(waste_vars[i] for i in bpp.BINS), "min_waste" for j in bpp.ITEMS: prob += lpSum(assign_vars[i, j] for i in bpp.BINS) == 1 for i in bpp.BINS: prob.relaxation[i] += (lpSum(bpp.volume[j] * assign_vars[i, j] for j in bpp.ITEMS) + waste_vars[i] == bpp.capacity * use_vars[i]) for i in bpp.BINS: for j in bpp.ITEMS: prob.relaxation[i] += assign_vars[i, j] <= use_vars[i] if args.antisymmetryCutsBins: for m in range(0, len(bpp.BINS) - 1): prob += use_vars[bpp.BINS[m]] >= use_vars[bpp.BINS[m + 1]] if args.antisymmetryCutsItems: for m in range(0, len(bpp.BINS)): for n in range(0, len(bpp.ITEMS)): if m > n: i = bpp.BINS[m] j = bpp.ITEMS[n] prob += assign_vars[i, j] == 0 # Attach the problem data and variable dictionaries # to the DipProblem prob.bpp = bpp prob.assign_vars = assign_vars prob.use_vars = use_vars prob.waste_vars = waste_vars prob.tol = pow(pow(2, -24), old_div(2.0, 3.0)) return prob
def formulate(args): prob = DipProblem("MILP") numBlocks = args.numBlocks numBlockVars = [args.numVarsPerBlock for i in range(numBlocks)] numBlockCons = [args.numConsPerBlock for j in range(numBlocks)] numVars = sum(numBlockVars) numCons = sum(numBlockCons) + args.numLinkingCons VARIABLES = dict(((i, j), 0) for i in range(numBlocks) for j in range(numBlockVars[i])) CONSTRAINTS = [] for k in range(numBlocks): CONSTRAINTS.append(["C"+str(k)+"_"+str(j) for j in range(numCons)]) CONSTRAINTS.append(["C"+str(numBlocks)+"_"+str(j) for j in range(numCons)]) #Generate random MILP var = LpVariable.dicts("x", VARIABLES, 0, 1, LpBinary) OBJ, MAT, RHS = GenerateRandomBlock(VARIABLES, CONSTRAINTS[numBlocks], rand_seed = args.randomSeed, tightness = args.tightness, density = args.density) prob += -lpSum([OBJ[i]*var[i] for i in var]), "Objective" #Linking constraints for j in CONSTRAINTS[numBlocks]: prob += lpSum([MAT[i, j]*var[i] for i in var]) <= RHS[j], j #Blocks for k in range(numBlocks): OBJ, MAT, RHS = GenerateRandomBlock([(k, i) for i in range(numBlockVars[k])], CONSTRAINTS[k]) for j in CONSTRAINTS[k]: prob.relaxation[k] += (lpSum([MAT[(k, i), j]*var[k, i] for i in range(numBlockVars[k])]) <=RHS[j], j) return prob
def formulate(args): FIXED_COST = None ASSIGNMENTS = None ASSIGNMENT_COSTS = None if args.module: m = ilib.import_module(args.module) LOCATIONS = m.LOCATIONS PRODUCTS = m.PRODUCTS DEMAND = m.DEMAND CAPACITY = m.CAPACITY if hasattr(m, 'FIXED_COST'): FIXED_COST = m.FIXED_COST if hasattr(m, 'ASSIGNMENTS'): ASSIGNMENTS = m.ASSIGNMENTS if hasattr(m, 'ASSIGNMENT_COSTS'): ASSIGNMENT_COSTS = m.ASSIGNMENT_COSTS else: LOCATIONS = range(args.numLocations) PRODUCTS = range(args.numProducts) DEMAND = [int(i) for i in args.demands] CAPACITY = args.capacity if args.fixedCosts != None: FIXED_COST = [int(i) for i in args.fixedCosts] if FIXED_COST == None: FIXED_COST = {i: 1 for i in LOCATIONS} if ASSIGNMENTS == None: ASSIGNMENTS = [(i, j) for i in LOCATIONS for j in PRODUCTS] if ASSIGNMENT_COSTS == None: ASSIGNMENT_COSTS = {i: 0 for i in ASSIGNMENTS} prob = DipProblem("Facility Location") assign_vars = LpVariable.dicts("x", ASSIGNMENTS, 0, 1, LpBinary) use_vars = LpVariable.dicts("y", LOCATIONS, 0, 1, LpBinary) prob += (lpSum(use_vars[i] * FIXED_COST[i] for i in LOCATIONS) + lpSum(assign_vars[j] * ASSIGNMENT_COSTS[j] for j in ASSIGNMENTS), "min") # assignment constraints for j in PRODUCTS: prob += lpSum(assign_vars[(i, j)] for i in LOCATIONS) == 1 # Aggregate capacity constraints for i in LOCATIONS: prob.relaxation[i] += lpSum( assign_vars[(i, j)] * DEMAND[j] for j in PRODUCTS) <= CAPACITY * use_vars[i] # Disaggregate capacity constraints for i, j in ASSIGNMENTS: prob.relaxation[i] += assign_vars[(i, j)] <= use_vars[i] prob.LOCATIONS = LOCATIONS prob.PRODUCTS = PRODUCTS prob.assign_vars = assign_vars prob.use_vars = use_vars return prob
args = parser.parse_args() #create the set of possible tables tables = list(range(max_tables)) possible_seatings = [(g, t) for g in guests for t in tables] #create a binary variable to model if a guest sits at a particular table x = pulp.LpVariable.dicts('possible_seatings', possible_seatings, lowBound=0, upBound=1, cat=pulp.LpInteger) seating_model = DipProblem("Wedding Seating Model (DIP)", pulp.LpMinimize, display_mode='off', display_interval=10000) #specify the maximum number of guests per table for table in tables: seating_model.relaxation[table] += sum([x[(guest, table)] for guest in guests]) <= \ max_table_size, \ "Maximum_table_size_%s"%table #A guest must seated at one and only one table for guest in guests: seating_model += (sum([x[(guest, table)] for table in tables]) == 1, "Must_seat_%s" % guest) #create a set of variables to model the objective function