自从我进行任何优化以来已经有几年了,我准备通过 Pyomo 使用 LP 解决交通问题。
最小化问题:
这个问题很容易解决,我做了类似的事情(更改了 Pyomo 文档中的教程代码):
from pyomo.environ import *
from pyomo.opt import SolverFactory
# create Pyomo model objects
demand = {'p1': 750, 'p2': 600, 'p3': 500, 'p4': 800}
supply = {'s1': 400, 's2': 600, 's3': 750, 's4': 300, 's5': 800}
combos = tuple(product(demand.keys(), supply.keys()))
vals = [114, 145, 153, 158, 163,
155, 180, 190, 194, 202,
135, 160, 172, 176, 185,
142, 171, 180, 185, 194]
T = dict(zip(combos, vals))
# create model instance
model3 = ConcreteModel()
model3.dual = Suffix(direction=Suffix.IMPORT)
# define index sets
plants = list(demand.keys())
suppliers = list(supply.keys())
# define the decision
model3.x = Var(plants, suppliers, domain=NonNegativeReals)
# define objective
@model3.Objective(sense=minimize)
def cost(m):
return sum([T[c,s]*model3.x[c,s] for c in plants for s in suppliers])
# constraints
@model3.Constraint(suppliers)
def src(m, s):
return sum([model3.x[c,s] for c in plants]) <= supply[s]
@model3.Constraint(plants)
def dmd(m, c):
return sum([model3.x[c,s] for s in suppliers]) == demand[c]
# solve
results = SolverFactory('glpk').solve(model3)
results.write()
# print results
if 'ok' == str(results.Solver.status):
print("Total Shipping Costs = ", model3.cost())
print("\nShipping Table:")
for s in suppliers:
for c in plants:
if model3.x[c,s]() > 0:
print("Ship from ", s," to ", c, ":", model3.x[c,s]())
else:
print("No Valid Solution Found")
这产生了一个我知道是正确的解决方案:
Solution:
- number of solutions: 0
number of solutions displayed: 0
Total Shipping Costs = 443600.0
Shipping Table:
Ship from s1 to p1 : 150.0
Ship from s1 to p4 : 250.0
Ship from s2 to p2 : 100.0
Ship from s2 to p3 : 500.0
Ship from s3 to p2 : 200.0
Ship from s3 to p4 : 550.0
Ship from s4 to p2 : 300.0
Ship from s5 to p1 : 600.0
我所坚持的是以下附加约束:
我相当确定我应该创建一个字典来表示这一点:
# added constraint
space_limit = [2, 1.5, 3, 1.2, 1.7]
supply_space = dict(zip(suppliers, space_limit))
我知道我应该添加另一个约束函数,但我对语法感到困惑。我正在努力解压 Pyomo 对象以查看“引擎盖下的内容”,因为我不能只打印内容直到它点击为止。
如有帮助,我们将不胜感激!
我的尝试(不是正确的答案):
@model3.Constraint(suppliers)
def capacity(m, s):
return(sum([supply_space[s] * model3.x[c, s] for c in plants])) <= 2000
# solve
results = SolverFactory('glpk').solve(model3)
results.write()
# print results
if 'ok' == str(results.Solver.status):
print("Total Shipping Costs = ", model3.cost())
print("\nShipping Table:")
for s in suppliers:
for c in plants:
if model3.x[c,s]() > 0:
print("Ship from ", s," to ", c, ":", model3.x[c,s]())
else:
print("No Valid Solution Found")
存储限制仅适用于 4 号工厂。您的约束很接近,但需要仅针对
p4
编写脚本,并且它是所有供应商的总和,而不是“每个供应商”约束。我期待这样的事情:
model3.cap_constraint = Constraint(expr=sum(model3.x['p4', s] * supply_space[s] for s in suppliers) <= 2000)