问题描述
我正在使用python的纸浆包编写线性编程。我对建立约束有疑问。
为说明此问题,请想象一个100 x 100厘米的正方形。我有几个不同尺寸的圆圈。我需要将这些圆圈包括在正方形中,以使直径面积的总和最大化。当第一行被填充时,第二行将形成在其上方,依此类推,始终将其视为约束:
每个圆只能在每一行中选择一次 圆的直径总和不能超过长度限制 圆的直径总和不能超过宽度限制 圆的面积之和不能大于正方形的面积 我的疑问在于约束3。我的想法是确定每一行的最大直径(也可以是平均值)。这些最大值的总和不能超过100的值。是否可以创建这样的约束?
“变量”
alocado = pulp.LpVariable.dicts("alocado",((n,t) for n,t in df.index),cat='Binary')
model = pulp.LpProblem("Alocacao_na_pilha",pulp.LpMaximize)
“目标函数”
model += pulp.lpSum(alocado[n,t] * df.loc[(n,t),'area']
for n,'z'
“设置”
circle= df.index.get_level_values(0).unique()
filled= df.index.get_level_values(1).unique()
“限制”
for n in circle:
model += pulp.lpSum(alocado[(n,t)] for t in filled) <= 1
for t in filled:
model += pulp.lpSum(alocado[(n,t)] * df.loc[(n,'d1'] for n in circle) <= 100
model += pulp.lpSum(pulp.lpSum(alocado[n,t] for t in filled) * df.loc[(n,'area'] for n in circle) <= 1000
“解决问题”
model.solve(pulp.PULP_CBC_CMD(maxSeconds=1000,msg=1,fracGap=0))
解决方法
欢迎您!
没有问题中的输入数据,我无法直接实现它,但是对每行的最大值之和设置约束应该很容易。下面的伪代码解决方案。
我要这样做的方法是引入一组新的变量-每行一个:
row_maxes = pulp.LpVariable.dicts("row_maxes",[i for i in range(n_rows)],cat='Continuous')
然后,您需要将这些变量限制为至少与每一行的最大圆一样大:
for i in range(n_rows):
for circle in i:
prob += row_maxes[i] >= circle.diameter
然后,您可以针对这些row_maxes的总和设置所需的约束:
prob += lpSum([row_maxes[i] for i in range(n_rows)]) <= 100
我们在这里依靠这样一个事实,即目标是尽可能多地融入圈子。在我们对每个row_maxes
的约束中,我们只需要在一侧设置约束-但这是我们为使圆环适合而在意的一侧。