TypeError PYOMO:基于 Pandas 数据框定义约束 [英] TypeError PYOMO: Defining constraints based on pandas dataframe

查看:32
本文介绍了TypeError PYOMO:基于 Pandas 数据框定义约束的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于一个优化问题,我试图在 PYOMO 中定义一个约束,其中约束表达式包含来自 Pandas DataFrame 的一些特定值.

For an optimization problem, I am trying to define a constraint in PYOMO, where the the constraint expression includes some specific values from a pandas DataFrame.

我会尽量用简洁的方式解释我的问题.

I will try to explain my problem in a concise way.

以下是进口.

from pyomo.environ import *
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt 
from pyomo.opt import SolverFactory

model = ConcreteModel()

以下是决策变量.

model.d1 = Var(bounds=(0.8,1.0), initialize = 0.9)
model.t1 = Var(bounds=(0.1,0.3))

目标函数如下:

model.Total_weight = Objective(expr=  model.t1*model.d1, sense= minimize )

为了制定约束表达式,我使用了 DataFrame 中的一些值.

To formulate a constraint expression, I am using some values from a DataFrame.

DataFrame 看起来像这样:

The DataFrame would look like this:

r1 = [50.05,60.0,70]
r2 = [100,150,200]

df = pd.DataFrame([r1,r2])

        0      1    2
0   50.05   60.0   70
1  100.00  150.0  200

目前的想法:

我将 df 中的一些值分配给变量,以便在约束表达式中使用(如下所示).

I am assigning some of the values from the df to variables, in order to be used in the constraint expression (as shown below).

v1 = df.iloc[0, 1]
v2 = df.iloc[1,1]

v1 和 v2 的唯一目的是将值输入到约束表达式中.与优化模型无关.

The only purpose of v1 and v2 is to input value to the constraint expression. It has nothing to do with the optimization model.

model.C1 = Constraint(expr =  v1 +  v2 *model.d1 <= 2.1)

但是我在执行这个想法时遇到了以下错误

But I got the following error while executing this idea

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-9-a9a7f2887bcb> in <module>
----> 1 model.C1 = Constraint(expr = v1 +  v2 *model.d1)

TypeError: unsupported operand type(s) for *: 'float' and 'NoneType'

据我所知,python 将 v1 和 v2 视为float",model.d1 被视为NoneType".我试图通过将 initialize 添加到变量 model.d1 来运行模型.但它似乎仍然是NoneType".

To my understanding, python considers v1 and v2 as 'float' and model.d1 is considered as 'NoneType'. I tried to run the model by adding initialize to the variable model.d1. But still it seems 'NoneType'.

有人可以帮我解决这个问题吗?

Can someone please help me to solve this?

非常感谢您.

PS:model.d1.display() 给出以下输出.

PS: model.d1.display() gives following output.

d1 : Size=1, Index=None
    Key  : Lower : Value : Upper : Fixed : Stale : Domain
    None :   0.8 :   0.9 :   1.0 : False : False :  Reals

推荐答案

因此,当 pyomo 如何与 numpy 值交互时,您可能偶然发现了一个小错误.code>pyomo 变量是一个单例......我认为这不会经常出现,因为在处理索引的 pyomo 变量时问题不会暴露自己,这是迄今为止大多数情况.你的是未编入索引的单身人士.

So you might have stumbled onto a small bug in how pyomo interacts with numpy values when the pyomo variable is a singleton.... I don't think this comes up too often as the problem does not expose itself when dealing with indexed pyomo variables, which is by far the majority case. Yours are non-indexed singletons.

首先,让您的模型正常工作.将来自 df 的值转换为浮点数,这很好用.

First, let's get your model working. Convert the values coming out of your df into floats and this works fine.

from pyomo.environ import *
#import numpy as np
import pandas as pd
import matplotlib.pyplot as plt 
#from pyomo.opt import SolverFactory

model = ConcreteModel()

model.d1 = Var(bounds=(0.8,1.0), domain=NonNegativeReals)
model.t1 = Var(bounds=(0.1,0.3), domain=NonNegativeReals)

r1 = [50.05,60.0,70]
r2 = [100,150,200]

df = pd.DataFrame([r1,r2])

v1 = float(df.iloc[0, 1])   # NOTE the float() conversion
v2 = float(df.iloc[1, 1])   # NOTE the float() conversion

model.C1 = Constraint(expr=v1 + v2 * model.d1 <= 2.1)

model.pprint()

疑似错误...

这两个都应该按照我的理解执行.我几乎从不处理单例变量(未编入索引),所以这里可能还有其他事情.我会尝试将此作为错误提交给 pyomo 的人,看看会发生什么.

Both of these should execute by my understanding. I almost never deal w/ singleton variables (that are not indexed) so perhaps there is something else afoot here. I'll try to submit this to pyomo folks as a bug and see what comes of it.

from pyomo.environ import *
import numpy as np

c = np.float64(1.5)  # a numpy float like what comes out of a pd dataframe...

model_1 = ConcreteModel()

model_1.x = Var()

# a simple expression
e = c * model_1.x     # FAILS!  TypeError: unsupported operand type(s) for *: 'float' and 'NoneType'


model_2 = ConcreteModel()

model_2.S = Set(initialize = [1,])   # indexing set with 1 member

model_2.x = Var(model_2.S)

# same expression
e2 = c * model_2.x[1]  # Works fine...

这篇关于TypeError PYOMO:基于 Pandas 数据框定义约束的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆