2017-08-17 23 views
1

パルプを使った整数線形最適化を解かなければなりません。私は問題を解決し、42に等しい最適化値を得る。しかし、ループ内で変数を宣言し、ループ内で制約を定義し、lpSum関数を使用して最適化を定義するなど、より一般的なコードを書いたとき、 私の問題は次の制約を定義することだと思います。整数PuLPによる線形最適化

for a in itemset_dict.keys(): 
    for b in itemset_dict[a][0]: 
     my_lp_program +=b >= a, "2Constraint" 

私は次の警告を得た:

C:\Program Files\Python36\lib\site-packages\pulp\pulp.py:1353: UserWarning: Overwriting previously set objective. 
    warnings.warn("Overwriting previously set objective.") 
Status: Optimal 
Total Optimum= None 
__dummy = None 
products_beer = 0.0 
products_cheese = 0.0 
products_cola = 0.0 
products_peanuts = 0.0 
The thread 'MainThread' (0xb30) has exited with code 0 (0x0). 
The program '[10140] python.exe' has exited with code 0 (0x0). 

はありがとうを。

 from pulp import * 

# defining list of products 
products = ['cola','peanuts', 'cheese', 'beer'] 
itemsets = ['x1','x2', 'x3'] 

#disctionary of the costs of each of the products is created 
costs = {'cola' : 5, 'peanuts' : 3, 'cheese' : 1, 'beer' : 4 } 

# dictionary of frequent itemsets 
itemset_dict = { "x1" : (("cola", "peanuts"),10), 
      "x2" : (("peanuts","cheese"),20), 
      "x3" : (("peanuts","beer"),30) 
      } 

products_var=LpVariable.dicts("Products", products, 0) 
itemsets_var=LpVariable.dicts("Itemsets", itemsets, 0) 

# defining itemsets variables 
''' 
for x in itemsets: 
    x = LpVariable('x', lowBound=0, upBound=1, cat='Binary') 
    ''' 
#x = LpVariable.dicts("x", itemsets, lowBound=0, upBound=1, cat='Binary') 


#option2 
i1=LpVariable.dict("itemsets", itemsets, lowBound=0, upBound=1, cat='Binary') 
#print(i1); 
#print(i1['x1']) 
#print(type(i1['x1'])) 

''' 
x1 = LpVariable('x1', lowBound=0, upBound=1, cat='Binary') 
x2 = LpVariable('x2', lowBound=0, upBound=1, cat='Binary') 
x3 = LpVariable('x3', lowBound=0, upBound=1, cat='Binary') 
''' 


# defining products variables 
''' 
for p in products: 
    p = LpVariable(p, lowBound=0, upBound=1, cat='Binary') 
    ''' 

#p = [LpVariable.dicts("p", i, lowBound=0, upBound=1, cat='Binary') for i in products] 

''' 
option1 
p=[LpVariable(i, lowBound=0, upBound=1, cat='Binary') for i in products] 
print(p[2]) 
print(type(p[2])) 
''' 


#option2 
p1=LpVariable.dict("products", products, lowBound=0, upBound=1, cat='Binary') 
#print(p1); 
#print(p1['cola']) 
#print(type(p1['cola'])) 

''' 
cola = LpVariable('cola', lowBound=0, upBound=1, cat='Binary') 
peanuts = LpVariable('peanuts', lowBound=0, upBound=1, cat='Binary') 
cheese = LpVariable('cheese', lowBound=0, upBound=1, cat='Binary') 
beer = LpVariable('beer', lowBound=0, upBound=1, cat='Binary') 
''' 


my_lp_program = LpProblem('My LP Problem', LpMaximize) 

#my_lp_program += 10*x1+20*x2+30*x3-5*p1-3*p2-1*p3-4*p4 , "Maximization" 
#my_lp_program += 10*x1+20*x2+30*x3 - lpSum([costs[i] * p1[i] for i in products]) , "Maximization" 
my_lp_program += lpSum([itemset_dict[i][1] * i1[i] for i in itemsets]) - lpSum([costs[i] * p1[i] for i in products]) , "Maximization" 
#my_lp_program += lpSum([itemset_dict[i][1] * itemsets_var[i] for i in itemsets]) - lpSum([costs[i] * products_var[i] for i in products]) , "Maximization" 


#my_lp_program +=cola+peanuts+cheese+beer<=3, "1Constained" 


my_lp_program +=lpSum([p1[i] for i in products]) <= 3, "1Constaint" 


''' 
my_lp_program +=cola>=x1, "2Constained" 
my_lp_program +=peanuts>=x1, "3Constained" 
my_lp_program +=peanuts>=x2, "4Constained" 
my_lp_program +=cheese>=x2, "5Constained" 
my_lp_program +=peanuts>=x3, "6Constained" 
my_lp_program +=beer>=x3, "7Constained" 
''' 


for a in itemset_dict.keys(): 
    for b in itemset_dict[a][0]: 
     my_lp_program +=b >= a, "2Constraint" 


my_lp_program.writeLP("CheckLpProgram.lp") 
my_lp_program.solve() 

print("Status:", LpStatus[my_lp_program.status]) 

print("Total Optimum=", value(my_lp_program.objective)) 

for v in my_lp_program.variables(): 
    print(v.name, "=", v.varValue) 
+0

それはあなたのアプローチでは、少なくとも2つの一般的なミス(私は今テストすることができないパルプの行動に応じて、多分1つ)があることは明らかだが、私は何が起こっているのかを詳細に説明するのではなく、「私は解決策がない」というように人々だけが言う理由を困惑させた。私はそれがエラーを出すと思うだろう(そして、私は今パルプにアクセスしていない)。それともそうではありませんか?あなたの質問を編集してください。 (btw:問題のあるライブラリの名前が正しく書かれているように、あなたのqestion-titleを編集します) – sascha

+0

あなたの答えをありがとう。私はコードを更新しました。私は進歩したと思う。私はまだ制約を定義することに問題があります。 –

答えて

2

私はあなたのコードをここに書き直して、実用的な解決策を提供しています。そのようなモデルをデバッグするのに役立つものについてのヒントを与えるコメントを見てください。

from pulp import * 

# defining list of products 
products = ['cola','peanuts', 'cheese', 'beer'] 
itemsets = ['x1','x2', 'x3'] 

#disctionary of the costs of each of the products is created 
costs = {'cola' : 5, 'peanuts' : 3, 'cheese' : 1, 'beer' : 4 } 

# dictionary of frequent itemsets 
# ~~> This is hard to maintain - I would select a different data structure 
# it gets really complicated below as you will see! 
itemset_dict = { "x1" : (("cola", "peanuts"),10), 
      "x2" : (("peanuts","cheese"),20), 
      "x3" : (("peanuts","beer"),30) 
      } 

# Good practice to first define your problem 
my_lp_program = LpProblem('My LP Problem', LpMaximize) 

# ~~>You do not need bounds for binary variables, they are automatically 0/1 
products_var=LpVariable.dicts("Products", products, cat='Binary') 
itemsets_var=LpVariable.dicts("Itemsets", itemsets, cat='Binary') 

# ~~> Not necessary - commended out 
# defining itemsets variables 
# for x in itemsets: 
#  x = LpVariable(x, lowBound=0, upBound=1, cat='Binary') 

''' 
x1 = LpVariable('x1', lowBound=0, upBound=1, cat='Binary') 
x2 = LpVariable('x2', lowBound=0, upBound=1, cat='Binary') 
x3 = LpVariable('x3', lowBound=0, upBound=1, cat='Binary') 
''' 

# ~~> Not necessary - commended out 
# defining products variables 
# for p in products: 
#  p = LpVariable(p, lowBound=0, upBound=1, cat='Binary') 

''' 
cola = LpVariable('cola', lowBound=0, upBound=1, cat='Binary') 
peanuts = LpVariable('peanuts', lowBound=0, upBound=1, cat='Binary') 
cheese = LpVariable('cheese', lowBound=0, upBound=1, cat='Binary') 
beer = LpVariable('beer', lowBound=0, upBound=1, cat='Binary') 
''' 

# ~~> Not necessary - commended out, see below 
#my_lp_program += 10*x1+20*x2+30*x3-5*p1-3*p2-1*p3-4*p4 , "Maximization" 
# my_lp_program += lpSum([itemset_dict[i][1] * itemsets_var[i] for i in itemsets]) - lpSum([costs[i] * products_var[i] for i in products]) , "Maximization" 

# ~~> Use an affine expression to define your objective. 
# ~~> Even better, define two objects as LpAffineExpression and add them, 
# ~~> it keeps the code cleaner 
my_lp_program += LpAffineExpression([(
    itemsets_var[x], itemset_dict[x][1]) for x in itemsets_var]) + \ 
    LpAffineExpression([(
    products_var[x], -costs[x]) for x in products_var]) 

# ~~> Not necessary - commended out 
#my_lp_program +=cola+peanuts+cheese+beer<=3, "1Constained" 
# my_lp_program +=lpSum([products_var[i] for i in products]) <= 3, "1Constaint" 
# ~~> This is the right way to enter this constraint. 
# ~~> I do not like the naming though.. 
my_lp_program += lpSum(products_var) <= 3, '1Constraint' 

''' 
my_lp_program +=cola>=x1, "2Constained" 
my_lp_program +=peanuts>=x1, "3Constained" 
my_lp_program +=peanuts>=x2, "4Constained" 
my_lp_program +=cheese>=x2, "5Constained" 
my_lp_program +=peanuts>=x3, "6Constained" 
my_lp_program +=beer>=x3, "7Constained" 
''' 
# ~~> Here are your constraints 
counter = 1 
for a in itemset_dict.keys(): 
    item = itemsets_var[a] 
    for b in itemset_dict[a][0]: 
     product = products_var[b] 
     counter +=1 
     my_lp_program += product >= item, "{}Constraint".format(counter) 

# ~~> Great that you export the lp! If you look at the file you can 
# ~~> spot a lot of issues with the model during debugging 
my_lp_program.writeLP("CheckLpProgram.lp") 
my_lp_program.solve() 

print("Status:", LpStatus[my_lp_program.status]) 

print("Total Optimum=", value(my_lp_program.objective)) 

for v in my_lp_program.variables(): 
    print(v.name, "=", v.varValue) 

出力:

('Status:', 'Optimal') 
('Total Optimum=', 42.0) 
('Itemsets_x1', '=', 0.0) 
('Itemsets_x2', '=', 1.0) 
('Itemsets_x3', '=', 1.0) 
('Products_beer', '=', 1.0) 
('Products_cheese', '=', 1.0) 
('Products_cola', '=', 0.0) 
('Products_peanuts', '=', 1.0) 
+0

ありがとう –

関連する問題