def main(input_path="ubicaciones.csv", balance_deviations=[0.1, 0.15, 0.2, 0.3]): """ Use different balance deviations to test complex lp function to minimize. Args: input_path : csv path with information regarding agencies, frequency, volume and coordinates balance_deviations = list with percentage of deviations, for calaculation refer to stops_gap and items_gap Returns: None """ df = pd.read_csv(input_path) df.loc[df[df["Vol_Entrega"] == 0].index, "Vol_Entrega"] = 1 zones = ["D1", "D2", "D3", "D4", "D5", "D6"] agencies = list("A" + df["Id_Cliente"].astype(str)) vol_delivery = list(df["Vol_Entrega"]) vol_stores = list(df["Vol_Entrega"] * df["Frecuencia"]) frequency = list(df["Frecuencia"]) stores_volume = dict(zip(agencies, vol_stores)) stores_frequency = dict(zip(agencies, frequency)) vol_delivery = dict(zip(agencies, vol_delivery)) scaler = MinMaxScaler() fitted_scaler = scaler.fit(df[["lat", "lon"]]) scaled_coordinates = fitted_scaler.transform(df[["lat", "lon"]]) kmeans = KMeansConstrained(n_clusters=6, size_min=604, size_max=605, random_state=12, n_init=100, max_iter=200, n_jobs=-1) kmeans_values = kmeans.fit(scaled_coordinates) df["kmeans"] = list(kmeans.predict(scaled_coordinates)) vectorized_lat_lon = df[["lat", "lon"]].to_numpy() cluster_centers = fitted_scaler.inverse_transform(kmeans.cluster_centers_) distance_matrix = cdist(cluster_centers, vectorized_lat_lon, metric="cityblock") routes = [(z, a) for z in zones for a in agencies] distances = pulp.makeDict([zones, agencies], distance_matrix, 0) flow = pulp.LpVariable.dicts("Distribution", (zones, agencies), 0, None) using = pulp.LpVariable.dicts("BelongstoZone", (zones, agencies), 0, 1, pulp.LpInteger) for percentage in balance_deviations: prob = pulp.LpProblem("BrewingDataCup2020_" + str(percentage), pulp.LpMinimize) prob += pulp.lpSum([ distances[z][a] * flow[z][a] for (z, a) in routes ]) + pulp.lpSum([distances[z][a] * using[z][a] for (z, a) in routes]), "totalCosts" stops_upper, stops_lower = stops_gap(percentage) distr_upper, distr_lower = items_gap(percentage) for z in zones: prob += pulp.lpSum([using[z][a] for a in agencies ]) <= stops_upper, "SumStopsInZoneUpper %s" % z prob += pulp.lpSum([using[z][a] for a in agencies ]) >= stops_lower, "SumStopsInZoneLower %s" % z prob += pulp.lpSum([flow[z][a] for a in agencies ]) <= distr_upper, "SumDistrInZoneUpper %s" % z prob += pulp.lpSum([flow[z][a] for a in agencies ]) >= distr_lower, "SumDistrInZoneLower %s" % z for z in zones: for a in agencies: prob += flow[z][a] - (100000 * using[z][a]) <= 0 prob += flow[z][a] <= vol_delivery[a] for a in agencies: prob += pulp.lpSum([flow[z][a] for z in zones ]) >= stores_volume[a], "Distribution %s" % a prob += pulp.lpSum([ using[z][a] for z in zones ]) == stores_frequency[a], "FrequencyDistribution %s" % a prob.writeLP("lp_files/milp_brewing_" + str(percentage) + ".lp") solver = pulp.CPLEX_CMD(path=path_to_cplex) prob.solve(solver) print("Estado: ", pulp.LpStatus[prob.status]) print("Total Cost: ", pulp.value(prob.objective)) final_df = pd.DataFrame(columns=["D1", "D2", "D3", "D4", "D5", "D6"], index=(range(1, 3626))) final_distr = dict() for v in prob.variables(): if (v.name).find("BelongstoZone_") == 0: if v.varValue > 0: dist = v.name[14:] zone = dist[:2] id_cliente = int(dist[4:]) final_df.loc[id_cliente, zone] = 1 final_df.fillna(0, inplace=True) final_df = final_df.astype(int).reset_index().rename( columns={"index": "Id_Cliente"}) final_df.to_csv("lp_solutions/cplex_opt_" + str(percentage) + "_" + str(pulp.value(prob.objective)) + ".csv", header=True, index=False)
def algorithm_run(): # Format course data df_course_info = format_course_info() df_course_info.drop(['course_unit'], axis=1, inplace=True) # Format applicant data df_ranking_info = format_rankings_info() df_ranking_info.drop(['course_unit', 'student_unit'], axis=1, inplace=True) # Format algortihm input courses = [] courses_supply = dict() for index, row in df_course_info.iterrows(): num_pos = row[3] + row[4] + row[5] + row[6] courses_supply[row[0]] = num_pos courses.append(row[0]) students = [] costs = {} for i in courses: costs[i] = [] temp = [] for index, row in df_ranking_info.iterrows(): if (row[1] not in students): students.append(row[1]) if (row[2] == 0 or row[3] == 0): temp.append([row[0], row[1], 0]) else: temp.append([row[0], row[1], row[2] + row[3]]) for i in temp: costs[i[0]].append(i[2]) student_demand = dict() for i in students: student_demand[i] = 1 costs_list = [] for i in courses: costs_list.append(costs[i]) # Algorithm run costs_list = pulp.makeDict([courses, students], costs_list, 0) prob = pulp.LpProblem("TA_Assignment", pulp.LpMaximize) assignment = [(c, s) for c in courses for s in students] x = pulp.LpVariable.dicts("decision", (courses, students), cat='Binary') prob += sum([ x[c][s] for (c, s) in assignment ]) - 0.01 * sum([x[c][s] * costs_list[c][s] for (c, s) in assignment]) for c in courses: prob += sum(x[c][s] for s in students) <= courses_supply[c], \ "Sum_of_TA_Positions_%s"%c for c in courses: for s in students: prob += x[c][s] <= costs_list[c][s], \ "Feasibility_{}_{}".format(s, c) for s in students: prob += sum(x[c][s] for c in courses) <= 1, \ "Sum_of_Students_%s"%s prob.solve() return x, costs_list, courses, students, courses_supply
def runPulp(matriz) : prop = pulp.LpProblem("Asignacion",pulp.LpMinimize) acts = [] d_acts = {} for j in range(len(matriz[0])): acts.append(f'A{j}') d_acts[f'A{j}'] = 1 turns = [] d_turns = {} for i in range(len(matriz)): turns.append(f'T{i}') d_turns[f'T{i}'] = 1 newM = makeMatriz(matriz) costos = pulp.makeDict([acts,turns],newM,0) asigns = [(c,b) for c in acts for b in turns] x = pulp.LpVariable.dicts("asigns", (acts,turns),lowBound = 0, cat = pulp.LpInteger) prop += sum(x[c][b] * costos [c][b] for (c,b) in asigns) #, \ "Suma_de_costos_de asigns" for c in acts: prop += sum([x[c][b] for b in turns]) == d_acts[c] #, \ "Suma_de_productos_que_salen_de_%s"%c for b in turns: prop += sum([x[c][b] for c in acts]) <= d_turns[b] #, \ "Suma_de_productos_que_entran_a_%s"%b prop.solve() solve = [] for v in prop.variables(): if v.varValue == 1.0 : s = v.name.split('_') s = s[1:] i = int(s[1][1:]) j = int(s[0][1:]) solve.append((i,j)) return solve
def modeloPulp(): global costos #Creamos el problema de transporte utilizando la variable prob prob = pulp.LpProblem("Problema_de_distribución", pulp.LpMinimize) # Convertimos los costos en un diccionario de PuLP costos = pulp.makeDict([ofertas, demandas], costos, 0) # Creamos una lista de tuplas que contiene todas las posibles rutas de tranporte. rutas = [(c, b) for c in ofertas for b in demandas] # creamos diccionario x que contendrá la candidad enviada en las rutas x = pulp.LpVariable.dicts("Ruta", (ofertas, demandas), lowBound=0, cat=pulp.LpInteger) # Agregamos la función objetivo al problema prob += sum([x[c][b]*costos[c][b] for (c,b) in rutas]), \ "Suma_de_costos_de_transporte" # Agregamos la restricción de máxima oferta de cada cervecería al problema. for c in ofertas: prob += sum([x[c][b] for b in demandas]) <= ofertas[c], \ "Suma_de_Productos_que_salen_de_fuentes_%s"%c # Agregamos la restricción de demanda mínima de cada bar for b in demandas: prob += sum([x[c][b] for c in ofertas]) >= demandas[b], \ "Suma_deProductos_que_entran_en_destinos%s"%b # Resolviendo el problema. prob.solve() cuadroTexto.insert(INSERT, "Valoración del resultado: \n\n") cuadroTexto.insert( INSERT, "Estado: {}".format(pulp.LpStatus[prob.status]) + "\n\n") cuadroTexto.insert( INSERT, "Mejor solución encontrada para cada variable de decisión: \n\n") # Imprimimos cada variable con su solución óptima. for v in prob.variables(): cuadroTexto.insert(INSERT, "{0:} = {1:}".format(v.name, v.varValue) + "\n") # Imprimimos el valor óptimo de la función objetivo cuadroTexto.insert(INSERT, "\nCosto total de transporte: \n \n") cuadroTexto.insert(INSERT, "Costo = {}".format(prob.objective.value()))
def __init__(self, home_list, work_list, util_matrix): """ Input a list of utils utils = [ #Works #1 2 3 4 5 [2,4,5,2,1],#A Homes [3,1,3,2,3] #B ] """ self.util_matrix = util_matrix self.homes = dict((home, home.houses) for home in home_list) self.works = dict((work, work.jobs) for work in work_list) self.utils = makeDict([home_list, work_list], util_matrix, 0) # Creates the 'prob' variable to contain the problem data self.prob = LpProblem("Residential Location Choice Problem", LpMinimize) # Creates a list of tuples containing all the possible location choices self.choices = [(h, w) for h in self.homes for w in self.works.keys()] # A dictionary called 'volumes' is created to contain the referenced variables(the choices) self.volumes = LpVariable.dicts("choice", (self.homes, self.works), 0, None, LpContinuous) # The objective function is added to 'prob' first self.prob += ( lpSum([self.volumes[h][w] * self.utils[h][w] for (h, w) in self.choices]), "Sum_of_Transporting_Costs", ) # The supply maximum constraints are added to prob for each supply node (home) for h in self.homes: self.prob += ( lpSum([self.volumes[h][w] for w in self.works]) <= self.homes[h], "Sum_of_Products_out_of_Home_%s" % h, ) # The demand minimum constraints are added to prob for each demand node (work) for w in self.works: self.prob += ( lpSum([self.volumes[h][w] for h in self.homes]) >= self.works[w], "Sum_of_Products_into_Work%s" % w, )
def __init__(self, home_list, work_list, util_matrix): """ Input a list of utils utils = [ #Works #1 2 3 4 5 [2,4,5,2,1],#A Homes [3,1,3,2,3] #B ] """ self.util_matrix = util_matrix self.homes = dict((home, home.houses) for home in home_list) self.works = dict((work, work.jobs) for work in work_list) self.utils = makeDict([home_list, work_list], util_matrix, 0) # Creates the 'prob' variable to contain the problem data self.prob = LpProblem("Residential Location Choice Problem", LpMinimize) # Creates a list of tuples containing all the possible location choices self.choices = [(h, w) for h in self.homes for w in self.works.keys()] # A dictionary called 'volumes' is created to contain the referenced variables(the choices) self.volumes = LpVariable.dicts("choice", (self.homes, self.works), 0, None, LpContinuous) # The objective function is added to 'prob' first self.prob += lpSum([ self.volumes[h][w] * self.utils[h][w] for (h, w) in self.choices ]), "Sum_of_Transporting_Costs" # The supply maximum constraints are added to prob for each supply node (home) for h in self.homes: self.prob += lpSum([ self.volumes[h][w] for w in self.works ]) <= self.homes[h], "Sum_of_Products_out_of_Home_%s" % h # The demand minimum constraints are added to prob for each demand node (work) for w in self.works: self.prob += lpSum([ self.volumes[h][w] for h in self.homes ]) >= self.works[w], "Sum_of_Products_into_Work%s" % w
import pulp, inspect from libs import Log, Timed time_limit = 10 n = 10 capacity = 165 index = map(str, range(n)) weights = pulp.makeDict([index], [23, 31, 29, 44, 53, 38, 63, 85, 89, 82]) values = pulp.makeDict([index], [92, 57, 49, 68, 60, 43, 67, 84, 87, 72]) lp_vars = pulp.LpVariable.dicts("x", index, 0, 1, pulp.LpInteger) prob = pulp.LpProblem("Knapsack Problem", sense=pulp.LpMaximize) prob += pulp.lpSum([lp_vars[i] * values[i] for i in index]), "Total_Value" prob += pulp.lpSum([lp_vars[i] * weights[i] for i in index]) <= capacity, "Capacity" prob.solve() Log.info(pulp.LpStatus[prob.status]) Log.info(pulp.value(prob.objective)) for v in prob.variables(): Log(v.name + ' = ' + str(v.varValue))
block[d] = 1 for r in mealrecs['recipes']: grid.append((s, d, r)) arrays = [steptypes, daydim] ind = pd.MultiIndex.from_product(arrays) costmat = pd.DataFrame([], columns=ind, index=mealrecs['recipes']) for a in adirs: steps = a['steps'] for stp in steps: costmat[stp['type']].loc[a['Name']] = stp['time'] costl = np.zeros((noofdays, len(mealrecs['recipes']), len(steptypes))) for cnt, s in enumerate(steptypes): costl[cnt] = costmat[s].values costs = makeDict([steptypes, daydim, mealrecs['recipes']], costl, 0) objfunc = [] #objfunc+=[x[s][d][r]*costs[s][d][r] for (s,d,r) in grid] for d in daydim: block.update(dict.fromkeys(daydim, 1)) block[d] = 0 for s in steptypes: objfunc += [ x[s][d][r] * costs[s][d][r] - reduction[s] * x[s][d][r] for r in mealrecs['recipes'] ]
# Creates a dictionary for the number of units of demand for each demand node demand = {"1":500, "2":900, "3":1800, "4":200, "5":700,} # Creates a list of costs of each transportation path costs = [ #Bars #1 2 3 4 5 [2,4,5,2,1],#A Warehouses [3,1,3,2,3] #B ] # The cost data is made into a dictionary costs = pulp.makeDict([warehouses, bars], costs, 0) # Creates the 'prob' variable to contain the problem data prob = pulp.LpProblem("Beer Distribution Problem", pulp.LpMinimize) # Creates a list of all tuples containing all the possible routes for transport routes = [(w,b) for w in warehouses for b in bars] # A dictionary called x is created to contain quantity shipped on the routes x = pulp.LpVariable.dicts("routes", (warehouses, bars), lowBound = 0, cat = pulp.LpInteger) # The objective function is added to 'prob' first prob += sum([x[w][b]*costs[w][b] for (w,b) in routes]), \ "Sum_of_Transporting_Costs"
# Creates a dictionary for the number of units of demand for each demand node demand = {"1":500, "2":900, "3":1800, "4":200, "5":700,} # Creates a list of costs of each transportation path costs = [ #Bars #1 2 3 4 5 [2,4,5,2,1],#A Warehouses [3,1,3,2,3] #B ] # The cost data is made into a dictionary costs = pulp.makeDict([warehouses, bars], costs,0) # Creates the 'prob' variable to contain the problem data prob = pulp.LpProblem("Beer Distribution Problem", pulp.LpMinimize) # Creates a list of tuples containing all the possible routes for transport routes = [(w,b) for w in warehouses for b in bars] # A dictionary called x is created to contain quantity shipped on the routes x = pulp.LpVariable.dicts("route", (warehouses, bars), lowBound = 0, cat = pulp.LpInteger) # The objective function is added to 'prob' first prob += sum([x[w][b]*costs[w][b] for (w,b) in routes]), \ "Sum_of_Transporting_Costs"
# diccionario con la capacidad de demanda de cada bar demanda = {"Bar 1":500, "Bar 2":900, "Bar 3":1800, "Bar 4":200, "Bar 5":700,} # Lista con los costos de transporte de cada nodo costos = [ #Bares [2,4,5,2,1],# Cervecerías [3,1,3,2,3] ] # Convertimos los costos en un diccionario de PuLP costos = pulp.makeDict([cervecerias, bares], costos,0) # Creamos una lista de tuplas que contiene todas las posibles rutas de tranporte. rutas = [(c,b) for c in cervecerias for b in bares] # In[9]: # creamos diccionario x que contendrá la candidad enviada en las rutas x = pulp.LpVariable.dicts("ruta", (cervecerias, bares), lowBound = 0, cat = pulp.LpInteger) # Agregamos la función objetivo al problema prob += sum([x[c][b]*costos[c][b] for (c,b) in rutas]), "Suma_de_costos_de_transporte"
def permutation(centers_cells_space_time_in_omega0,centers_cells_space_time_in_omega1): nb_elt = len(centers_cells_space_time_in_omega0) # construction of the constraint matrix for the minimisation '''A_eq = np.zeros((2*nb_elt,nb_elt**2)) for i in range(nb_elt): for j in range(nb_elt): A_eq[i,j+i*nb_elt] = 1.0 for i in range(nb_elt): for j in range(nb_elt): A_eq[i+nb_elt,(j-1)*nb_elt+i] = 1.0 b_eq = np.ones(2*nb_elt)''' # computation of the different cost costs = np.array(np.zeros((nb_elt,nb_elt))) for i in range(nb_elt): for j in range(nb_elt): x0 = centers_cells_space_time_in_omega0[i,0] y0 = centers_cells_space_time_in_omega0[i,1] t0 = centers_cells_space_time_in_omega0[i,2] x1 = centers_cells_space_time_in_omega1[j,0] y1 = centers_cells_space_time_in_omega1[j,1] t1 = centers_cells_space_time_in_omega1[j,2] costs[i,j] = cost(x0,y0,t0,x1,y1,t1) #print(np.sum(costs)/nb_elt) # Creates a list of all the supply nodes warehouses = range(nb_elt) # Creates a list of all demand nodes bars = range(nb_elt) # The cost data is made into a dictionary costs_dic = pulp.makeDict([warehouses, bars], costs,0) # Creates the prob variable to contain the problem data prob = pulp.LpProblem("Beer Distribution Problem", pulp.LpMinimize) # Creates a list of tuples containing all the possible routes for transport routes = [(w,b) for w in warehouses for b in bars] # A dictionary called x is created to contain quantity shipped on the routes x = pulp.LpVariable.dicts("route", (warehouses, bars), lowBound = 0, cat = pulp.LpInteger) # The objective function is added to prob first prob += sum([x[w][b]*costs_dic[w][b] for (w,b) in routes]), "Sum_of_Transporting_Costs" # Supply maximum constraints are added to prob for each supply node (warehouse) for w in warehouses: prob += sum([x[w][b] for b in bars]) == 1, "Sum_of_Products_out_of_Warehouse_%s"%w # Demand minimum constraints are added to prob for each demand node (bar) for b in bars: prob += sum([x[w][b] for w in warehouses]) == 1, "Sum_of_Products_into_Bar%s"%b # The problem data is written to an .lp file #prob.writeLP("BeerDistributionProblem.lp") # The problem is solved using PuLPs choice of Solver prob.solve() # The status of the solution is printed to the screen print("Status:", pulp.LpStatus[prob.status]) # Each of the variables is printed with its resolved optimum value #for v in prob.variables(): # print v.name, "=", v.varValue A = np.zeros((nb_elt,nb_elt)) for i in range(nb_elt): for j in range(nb_elt): A[i,j] = x[i][j].value() #print A # The optimised objective function value is printed to the screen print("Total Cost of Transportation = ", prob.objective.value()) costs2 = A*np.transpose(np.matrix(costs)) #print(costs) #print(costs2) '''J1 = 0 J2 = 0 for i in range(nb_elt): J1 += costs[i,i] J2 += costs2[i,i] print('J1',J1) print('J2',J2)''' return A
costmat = pd.DataFrame([], columns=recipes.index, index=ings.index) costmat.fillna(ln, inplace=True) ings['costperquant'] = ings.cost / ings.quant for col in costmat.columns: if col != 'dump': rec = recipes[col:col] includedings = pd.DataFrame(rec.ingredients[0]).name costmat.loc[costmat[col].index.isin(includedings), col] = ings.costperquant[includedings] else: costmat[col] = ings.costperquant costsl = costmat.values.tolist() costs = makeDict([supl, deml], costsl, 0) x = LpVariable.dicts("route_", (supl, deml), lowBound=0, cat=LpContinuous) xb = LpVariable.dicts("choice_", (deml), lowBound=0, upBound=1, cat=LpBinary) xi = LpVariable.dicts("items_", (supl, deml), lowBound=0, upBound=1, cat=LpInteger) prob = LpProblem("Testing", LpMinimize) objfunc = [] objfunc += [x[w][b] * costs[w][b] for (w, b) in grid]
from pulp import makeDict, LpProblem, LpMaximize, LpVariable, lpSum, solvers, LpStatus, value #from Data import from Inventory import* from Tariff import * from BOM import * import time import winsound from SQL_Load import s_per, f_per, bound_capital sto_dem2 = [1.028, 1.057, 1.087] # The data is made into a dictionary supply = makeDict([production, product], supply,0) cost_produce = makeDict([production, product], cost_produce,0) container_cap = makeDict([product], container_cap,0) fam_fix = makeDict([nr_families, production], fam_fix_data,0) item_family = makeDict([nr_families, product], fam_bin, 0) selling_price = makeDict([country, product], selling_price, 0) demand = makeDict([country, product], demand_c,0) fly = makeDict([production, warehouse, product], fly,0) ship = makeDict([production, warehouse, product], sail,0) big_M_Fam = makeDict([nr_families, production], big_M_Fam,0) avg_inv = makeDict([year, production, warehouse, product], avg_inven,0) holding = makeDict([warehouse, product], holding_cost, 0) growth_per_production = makeDict([production], growth_produce, 0) sto_dem = makeDict([year], sto_dem2, 0) year_seq = makeDict([year], year_sequence, 0) growth_per_dem = makeDict([country, product], dem_grow, 0) taa_dem = makeDict([production, country, product], taa_demand,0) taa_dem_grow = makeDict([production, country, year_sequence], taa_list,0) wh_country = makeDict([warehouse, country], wh_cou,0) tariff = makeDict([production, country, product], tariffs,0)
def solveWithSolver(dicProducers, Campus, dicDemand, dicCostsMatrix, dicCapacities, dicVehicle, dist): for camp in Campus: campus = [camp] for day in dicDemand[camp]: print('campus : ', camp, ', jour : ', day) supply = dicDemand[camp][day] # print('supply', supply) Producers = dicProducers[camp] # print('producers', Producers) vehicle = dicVehicle[camp] # print('vehicle', vehicle) Capacity = dicCapacities[camp] # print('Capacities', Capacity) transportation_costs = dicCostsMatrix[camp] # print('Matrix', transportation_costs) costs = pulp.makeDict([campus + Producers, campus + Producers], transportation_costs, 0) distance_max = int(dist) Np = len(Producers) Vehicle = [(i, k) for i in campus + Producers for k in Producers] Routes = [(i, j, k) for i in campus + Producers for j in campus + Producers for k in Producers] # lp variable declaration vars_routes = pulp.LpVariable.dicts( "Route", (campus + Producers, campus + Producers, Producers), 0, None, pulp.LpBinary) vars_visit = pulp.LpVariable.dicts("Visit", (campus + Producers, Producers), 0, None, pulp.LpBinary) # problem and objective fonction prob = pulp.LpProblem("Coopain_VRP_Problem", pulp.LpMinimize) prob += pulp.lpSum([ vars_routes[i][j][k] * costs[i][j] for (i, j, k) in Routes ]), "Sum_of_Transporting_Costs" # Producers can only be visited 1 time for i in Producers: prob += pulp.lpSum( vars_visit[i][k] for k in Producers) == 1, "visit_of_producers{0}".format(i) # Only 1 route by producer for k in Producers: for i in campus + Producers: prob += (pulp.lpSum([vars_routes[i][j][k] for j in campus + Producers]) + pulp.lpSum([vars_routes[j][i][k] for j in campus + Producers])) \ <= 2, "visit_of_vehicle{0}_{1}".format(k, i) # disable routes from a producer to directely himself for i in campus + Producers: prob += pulp.lpSum([vars_routes[i][i][k] for k in Producers ]) == 0, "no_autovisit{0}".format(i) # conservation of flux 1 for i in campus + Producers: for k in Producers: prob += pulp.lpSum([vars_routes[i][j][k] for j in campus + Producers]) \ == vars_visit[i][k], "visit_of_producers1_{0}_{1}".format(i, k) # conservation of flux 2 for i in campus + Producers: for k in Producers: prob += pulp.lpSum([vars_routes[j][i][k] for j in campus + Producers]) \ == vars_visit[i][k], "visit_of_producers2_{0}_{1}".format(i, k) # an inexistent vehicle can't do a path for k in Producers: prob += pulp.lpSum([vars_routes[i][j][k] for i in campus + Producers for j in campus + Producers]) \ <= 2*Np*vehicle[k], "vehicle_exists{0}".format(k) # a producer who uses his vehicle is at the beginnig of a loop for k in Producers: prob += pulp.lpSum([vars_visit[i][k] for i in Producers]) \ <= 2 * Np * vars_routes[campus[0]][k][k], "first_place{0}".format(k) # a producer can't use his vehicle too much for k in Producers: prob += pulp.lpSum([vars_routes[i][j][k] * costs[i][j] for i in campus + Producers for j in campus + Producers]) \ <= distance_max, "distance_max{0}".format(k) # a vehicule have a capacity for k in Producers: prob += pulp.lpSum([vars_visit[i][k] * supply[i] for i in Producers]) \ <= Capacity[k], "respect_capacity{0}".format(k) # no underloop for subset in rt.powerset(Producers): longueur = len(subset) subset_id = "" for m in range(longueur): subset_id += subset[m] + "_" for k in Producers: prob += pulp.lpSum([vars_routes[i][j][k] for i in subset for j in subset]) \ <= longueur-1, "no_underloop_{0}{1}".format(subset_id, k) # The problem data is written to an .lp file # prob.writeLP("CoopainVRPProblem.lp") # The problem is solved using Cplex # prob.solve(pulp.getSolver('GUROBI_CMD', timeLimit=10)) prob.solve(pulp.PULP_CBC_CMD(fracGap=0)) # The status of the solution is printed to the screen # print("Status:", pulp.LpStatus[prob.status]) # Each significant variables is in listeRoute listeRoute = [] for v in prob.variables(): if v.varValue and v.name[:6] == 'Route_': listeRoute.append(v.name[6:]) lenRoute = len(listeRoute) # initialisation des dictionnaires dictResultat: Dict[str, List[str]] = {} dictRoute: Dict[str, List[str]] = {} for i in range(lenRoute): for j in range(len(listeRoute[i])): if listeRoute[i][-j - 1:] in Producers: dictResultat[listeRoute[i][-j - 1:]] = [] dictRoute[listeRoute[i][-j - 1:]] = [] # remplissage de dictRoute for i in range(lenRoute): for j in range(len(listeRoute[i])): if listeRoute[i][-j - 1:] in Producers: dictRoute[listeRoute[i][-j - 1:]].append( listeRoute[i][:-j - 2]) # remplissage de dictResultat for vehicule in [*dictRoute]: finBoucle = 0 visiteActuelle = vehicule while (finBoucle == 0): for i in range(len(dictRoute[vehicule])): for j in range(len(dictRoute[vehicule][i])): if dictRoute[vehicule][i][:j] == visiteActuelle: if (finBoucle == 0): dictResultat[vehicule].append( visiteActuelle) visiteActuelle = dictRoute[vehicule][i][j + 1:] if visiteActuelle == vehicule: finBoucle = 1 dictResultat[vehicule].append(visiteActuelle) return dictResultat, pulp.value(prob.objective)
def dynamic(items,poids,valeur,Poids_Max): print "items =",items print "poids =",poids print "valeurs =",valeur print "Poids max =",Poids_Max #creation du tableau T=pulp.makeDict([items,[i for i in range(Poids_Max+1)]],[ [None for i in range(Poids_Max+1)] for j in range(len(items))]) #initialisation: item 1 for j in range(1,Poids_Max+1): if poids[1]<=j: T[1][j]=valeur[1] else: T[1][j]=0 for i in items: T[i][0]=0 #print 'i=%s' %1 #print T #programmation dynamique for i in items: if i>1: for j in range(1,Poids_Max+1): #print " " #print 'i=%s, j=%s' %(i,j) if j-poids[i]>=0: T[i][j]=max(T[i-1][j],valeur[i]+ T[i-1][j-poids[i]]) else: T[i][j]=T[i-1][j] #which items are in the solution? keep=[] i=items[-1] #print i j=Poids_Max while i>0 and j >0: if T[i][j]!=T[i-1][j]: #print T[i][j],"!=",T[i-1][j],"?" keep.append(i) j-=poids[i] i-=1 #print "i=",i if i==1: if T[i][j]>0: keep.append(i) i-=1 #print "i=",i #print keep tab=np.array([[T[i][j] for j in range(1,Poids_Max+1)]for i in items]) #print tab #print "select items:",keep #return T[items[-1]][Poids_Max] return (keep,T[items[-1]][Poids_Max])
# http://www.mit.edu/~jvielma/lectures/IAP2018/slides.pdf # Assign n workers to complete m tasks # At most one task per worker # Assume n = 3, m = 2 prob = LpProblem("Job Shop", LpMinimize) # Input # Time it takes worker n to complete task m timeInput = [[4, 3], [6, 5], [5, 6]] # Worker and Task IDs # Let's just use 0, 1, 2, etc... for this example workers = range(len(timeInput)) tasks = range(len(timeInput[1])) time = makeDict([workers, tasks], timeInput) # Decision variables # What worker is assigned to which task x = LpVariable.dicts("WorkerToTask", (workers, tasks), 0, 1, LpInteger) # Objective function # Minimize the total time worked prob += lpSum([time[w][t] * x[w][t] for w in workers for t in tasks]), "Objective" # Constraints # Each task must have one worker for t in tasks: prob += lpSum(x[w][t] for w in workers) == 1, "Task" + str(t)
def build_pulp_problem(): # Creates a list of all the supply nodes Plants = ["San Francisco", "Los Angeles", "Phoenix", "Denver"] # Creates a dictionary of lists for the number of units of supply at # each plant and the fixed cost of running each plant supplyData = { # Plant Supply Fixed Cost "San Francisco": [1700, 70000], "Los Angeles": [2000, 70000], "Phoenix": [1700, 65000], "Denver": [2000, 70000], } # Creates a list of all demand nodes Stores = ["San Diego", "Barstow", "Tucson", "Dallas"] # Creates a dictionary for the number of units of demand at each store demand = { # Store Demand "San Diego": 1700, "Barstow": 1000, "Tucson": 1500, "Dallas": 1200, } # Creates a list of costs for each transportation path costs = [ # Stores # SD BA TU DA [5, 3, 2, 6], # SF [4, 7, 8, 10], # LA Plants [6, 5, 3, 8], # PH [9, 8, 6, 5], # DE ] # Creates a list of tuples containing all the possible routes for transport Routes = [(p, s) for p in Plants for s in Stores] # Splits the dictionaries to be more understandable (supply, fixedCost) = pulp.splitDict(supplyData) # The cost data is made into a dictionary costs = pulp.makeDict([Plants, Stores], costs, 0) plants_stores = [(p, s) for p in Plants for s in Stores] # Creates the problem variables of the Flow on the Arcs flow = pulp.LpVariable.dicts("Route", plants_stores, 0, None, pulp.LpInteger) # Creates the master problem variables of whether to build the Plants or not build = pulp.LpVariable.dicts("BuildaPlant", Plants, 0, 1, pulp.LpInteger) # Creates the 'prob' variable to contain the problem data prob = pulp.LpProblem("Computer Plant Problem", pulp.LpMinimize) # The objective function is added to prob - The sum of the transportation costs and the building fixed costs prob += ( pulp.lpSum([flow[p, s] * costs[p][s] for (p, s) in Routes]) + pulp.lpSum([fixedCost[p] * build[p] for p in Plants]), "Total Costs", ) # The Supply maximum constraints are added for each supply node (plant) for p in Plants: prob += ( pulp.lpSum([flow[p, s] for s in Stores]) <= supply[p] * build[p], "Sum of Products out of Plant %s" % p, ) # The Demand minimum constraints are added for each demand node (store) for s in Stores: prob += ( pulp.lpSum([flow[p, s] for p in Plants]) >= demand[s], "Sum of Products into Stores %s" % s, ) return prob
def beer(): """ The Beer Distribution Problem for the PuLP Modeller Authors: Antony Phillips, Dr Stuart Mitchell 2007 """ # Creates a list of all the supply nodes warehouses = ["A", "B"] # Creates a dictionary for the number of units of supply for each supply node supply = {"A": 1000, "B": 4000} # Creates a list of all demand nodes bars = ["1", "2", "3", "4", "5"] # Creates a dictionary for the number of units of demand for each demand node demand = {"1": 500, "2":900, "3":1800, "4":200, "5":700,} # Creates a list of costs of each transportation path costs = [ # Bars # 1 2 3 4 5 [2, 4, 5, 2, 1], # A Warehouses [3, 1, 3, 2, 3] # B ] # Fixed Transportation cost fixedCosts = [ # Bars # 1 2 3 4 5 [20000, 20000, 20000, 20000, 20000], # A Warehouses [0, 0, 0, 0, 0] # B ] # The cost data is made into a dictionary costs = pulp.makeDict([warehouses, bars], costs, 0) # The cost data is made into a dictionary fixedCosts = pulp.makeDict([warehouses, bars], fixedCosts, 0) # Creates the prob variable to contain the problem data prob = pulp.LpProblem("Beer Distribution Problem", pulp.LpMinimize) # Creates a list of tuples containing all the possible routes for transport routes = [(w, b) for w in warehouses for b in bars] # A dictionary called x is created to contain quantity shipped on the routes x = pulp.LpVariable.dicts("route", (warehouses, bars), lowBound = 0, cat = pulp.LpInteger) # The objective function is added to prob first prob += sum([((x[w][b] * costs[w][b]) + fixedCosts[w][b]) for (w, b) in routes]), "Sum_of_Transporting_Costs" # Supply maximum constraints are added to prob for each supply node (warehouse) for w in warehouses: prob += sum([x[w][b] for b in bars]) <= supply[w], "Sum_of_Products_out_of_Warehouse_%s" % w # Demand minimum constraints are added to prob for each demand node (bar) for b in bars: prob += sum([x[w][b] for w in warehouses]) >= demand[b], \ "Sum_of_Products_into_Bar%s" % b # The problem data is written to an .lp file prob.writeLP("BeerDistributionProblem.lp") # The problem is solved using PuLP's choice of Solver prob.solve() # The status of the solution is printed to the screen print "Status:", pulp.LpStatus[prob.status] # Each of the variables is printed with it's resolved optimum value for v in prob.variables(): print v.name, "=", v.varValue # The optimised objective function value is printed to the screen print "Total Cost of Transportation = ", prob.objective.value()
# demand here for all the students will be 1 since they can only be assigned to at max 1 course student_demand = dict() for i in students: student_demand[i] = 1 costs_list = [] for i in courses: costs_list.append(costs[i]) ### Algorithm formulation ### costs_list = pulp.makeDict([courses, students], costs_list, 0) # create the LP object, set up as a maximization problem prob = pulp.LpProblem("TA_Assignment", pulp.LpMaximize) # create a list of possible assignments assignment = [(c,s) for c in courses for s in students] # variables created to determine optimal assignment x = pulp.LpVariable.dicts("decision", (courses, students), cat='Binary') prob += sum([x[c][s] for (c,s) in assignment]) - 0.01*sum([x[c][s]*costs_list[c][s] for (c,s) in assignment]) # add constraint for c in courses: prob += sum(x[c][s] for s in students) <= courses_supply[c], \ "Sum_of_TA_Positions_%s"%c
def transportation_problem(): # Creates a list of all the supply nodes. Warehouses = ["A", "B"] # Creates a dictionary for the number of units of supply for each supply node. supply = {"A": 1000, "B": 4000} # Creates a list of all demand nodes. Bars = ["1", "2", "3", "4", "5"] # Creates a dictionary for the number of units of demand for each demand node. demand = { "1":500, "2":900, "3":1800, "4":200, "5":700, } # Creates a list of costs of each transportation path. costs = [ # Bars. #1 2 3 4 5. [2, 4, 5, 2, 1], #A Warehouses. [3, 1, 3, 2, 3] #B ] # The cost data is made into a dictionary. costs = pulp.makeDict([Warehouses, Bars], costs, 0) # Creates the 'prob' variable to contain the problem data. prob = pulp.LpProblem("Beer Distribution Problem", pulp.LpMinimize) # Creates a list of tuples containing all the possible routes for transport. Routes = [(w, b) for w in Warehouses for b in Bars] # A dictionary called 'Vars' is created to contain the referenced variables(the routes). vars = pulp.LpVariable.dicts("Route", (Warehouses, Bars), 0, None, pulp.LpInteger) # The objective function is added to 'prob' first. prob += pulp.lpSum([vars[w][b] * costs[w][b] for (w, b) in Routes]), "Sum_of_Transporting_Costs" # The supply maximum constraints are added to prob for each supply node (warehouse). for w in Warehouses: prob += pulp.lpSum([vars[w][b] for b in Bars]) <= supply[w], "Sum_of_Products_out_of_Warehouse_{}".format(w) # The demand minimum constraints are added to prob for each demand node (bar). for b in Bars: prob += pulp.lpSum([vars[w][b] for w in Warehouses]) >= demand[b], "Sum_of_Products_into_Bar{}".format(b) # The problem data is written to an .lp file. prob.writeLP("./BeerDistributionProblem.lp") # The problem is solved using PuLP's choice of Solver. prob.solve() # The status of the solution is printed to the screen. print("Status: {}.".format(pulp.LpStatus[prob.status])) # Each of the variables is printed with it's resolved optimum value. for v in prob.variables(): print("\t{} = {}.".format(v.name, v.varValue)) # The optimised objective function value is printed to the screen. print("Total Cost of Transportation = {}.".format(pulp.value(prob.objective)))