杉数求解器这个案例很常见,我们直接讲代码吧。多商品问题约束其实好理解。
我们可以尝试一下做一下杉数官网的题目。
本文参考代码:muticommodity.py。
import coptpy as cp
from coptpy import COPT
import math
import itertools
日常导库奥。
ORIG = ['GARY', 'CLEV', 'PITT']
DEST = ['FRA', 'DET', 'LAN', 'WIN', 'STL', 'FRE', 'LAF']
PROD = ['bands', 'coils', 'plate']
解释一下,这个orig是原始地点列表,dest是目的地,prod是产品名称。
supply_list = [400, 800, 200,
700, 1600, 300,
800, 1800, 300]
supply = dict(zip(itertools.product(ORIG, PROD), supply_list))
这个是原始地点和供应量。字典这个功能别忘记了,是一个映射。(体会一下,很好理解的)好家伙这个地方可以求解这个题目了2024年亚太赛中文赛C题-一种常见的调度问题求解模型(含相似题对比和提示词工程)
demand_list = [300, 500, 100,
300, 750, 100,
100, 400, 0,
75, 250, 50,
650, 950, 200,
225, 850, 100,
250, 500, 250]
demand = dict(zip(itertools.product(DEST, PROD), demand_list))
这个是需求数据,那好我们讲通透一点吧。
limit_list = [625.0] * len(ORIG) * len(DEST)
limit = dict(zip(itertools.product(ORIG, DEST), limit_list))
#limit_list: 每个原始地点和目的地点间运输限制的列表。
#limit: 字典,将每个原始地点和目的地点的组合映射到运输限制
代码注释如上。
cost_list = [30, 39, 41,
10, 14, 15,
...
15, 20, 20]
cost = dict(zip(itertools.product(ORIG, DEST, PROD), cost_list))
这个是成本数据,代码设计的时候注意这个cost这一行,ORIG,DEST,PROD梦幻联动。
env = cp.Envr()
mmulti = env.createModel()
杉数行为,我们不解释,准备放大招。
vtrans = mmulti.addVars(ORIG, DEST, PROD, nameprefix='trans')
#vtrans: 定义了从每个原始地点到每个目的地点每种产品的运输量的决策变量
接下来三个约束
mmulti.addConstrs((vtrans.sum(i, '*', k) == supply[i, k] for i in ORIG for k in PROD), nameprefix='supply')
mmulti.addConstrs((vtrans.sum('*', j, k) == demand[j, k] for j in DEST for k in PROD), nameprefix='demand')
mmulti.addConstrs((vtrans.sum(i, j, '*') <= limit[i, j] for i in ORIG for j in DEST), nameprefix='multi')
#供应约束: 确保每种产品从每个原始地点运输的总量与供应相匹配。
#需求约束: 确保每种产品运输到每个目的地的总量与需求相匹配。
#多限制约束: 限制每个原始地点到每个目的地的总运输量。
接下来最小化运输成本
mmulti.setObjective(vtrans.prod(cost), COPT.MINIMIZE)
我们设置一个参数
mmulti.setParam(COPT.Param.TimeLimit, 100)
mmulti.solve()
第一是求解,其实设置的是求解时间,设置不设置不影响问题本身。
if mmulti.status == COPT.OPTIMAL:
print('\nObjective value: {}'.format(mmulti.objval))
print('Variable solution: ')
multvars = mmulti.getVars()
for mvar in multvars:
if math.fabs(mvar.x) >= 1e-6:
print(' {0:s} = {1:.6f}'.format(mvar.name, mvar.x))
这段代码是通用的代码,这下知道了吧。
这个问题本质上是混合整数规划问题。
Cardinal Optimizer v7.1.3. Build date Apr 29 2024
Copyright Cardinal Operations 2024. All Rights Reserved
Setting parameter 'TimeLimit' to 100
Model fingerprint: be2910e5
Using Cardinal Optimizer v7.1.3 on Windows
Hardware has 4 cores and 8 threads. Using instruction set X86_AVX512_E1 (14)
Minimizing an LP problem
The original problem has:
51 rows, 63 columns and 189 non-zero elements
The presolved problem has:
41 rows, 60 columns and 145 non-zero elements
Starting the simplex solver using up to 8 threads
Method Iteration Objective Primal.NInf Dual.NInf Time
Dual 0 0.0000000000e+00 26 0 0.02s
Dual 45 1.9951537592e+05 0 0 0.02s
Postsolving
Dual 45 1.9950000000e+05 0 0 0.02s
Solving finished
Status: Optimal Objective: 1.9950000000e+05 Iterations: 45 Time: 0.03s
Objective value: 199500.0
Variable solution:
400.000000 =
25.000000 =
200.000000 =
625.000000 =
150.000000 =
225.000000 =
50.000000 =
525.000000 =
100.000000 =
400.000000 =
150.000000 =
50.000000 =
250.000000 =
300.000000 =
225.000000 =
100.000000 =
225.000000 =
75.000000 =
500.000000 =
50.000000 =
300.000000 =
225.000000 =
100.000000 =
75.000000 =
100.000000 =
625.000000 =
225.000000 =
25.000000 =
350.000000 =
250.000000 =
这也太清楚了吧,爱了,结果显示:从哪到哪送啥玩意。
#Variable solution 列出了每个变量的解释。
#每行表示一条运输路径,格式为 trans(起始地点, 目的地点, 货物类型) = 数量。
#例如,trans(GARY, STL, bands) = 400.000000 表示从GARY到STL运输bands类型的货物400个单位。
我们看结果知道,我们使用的是双对偶法。
那好我们今天到这里吧。
最近北太天元在和杉数科技合作:
杉数科技与北太振寰达成战略合作,携手推动国产科学计算与智能决策融合发展
北太天元和杉数科技达成合作之后会让智能决策和科学计算领域飞速发展,让我们关注他们并且支持:
支持国产,我们一起努力!!!