涉及标量的 pyomo 的约束问题

Constraint issue with pyomo involving a scalar

处理 pyomo 的经济优化问题,我想添加一个约束以防止商品数量及其价格的乘积低于零 (<0),从而避免负收入。似乎所有数据都在一个数据框中,我无法设置如下约束:

def positive_revenue(model, t)
    return model.P * model.C >=0
model.positive_rev = Constraint(model.T, rule=positive_revenue)

系统return出现价格是标量的错误,无法处理。事实上,模型中的价格是这样设置的:

model.T = Set(doc='quarter of year', initialize=df.quarter.tolist(), ordered=True)



model.P = Param(initialize=df.price.tolist(), doc='Price for each quarter')

##while the commodity is:
model.C = Var(model.T, domain=NonNegativeReals)

我只想将其应用于每个时间步长(此处为一刻钟):

价格(t) * model.C(t) >=0

有人可以帮助我发现问题吗?谢谢

这里有更多信息:

df 数据帧:

df                   time_stamp  price Status  imbalance  
quarter                                                                                                                                  
0       2021-01-01 00:00:00  64.84  Final         16          
1       2021-01-01 00:15:00  13.96  Final         38          
2       2021-01-01 00:30:00  12.40  Final         46  

index = quarter 从 0 到 35049,所以没问题

Here is the df.info()
#   Column          Non-Null Count  Dtype         
---  ------          --------------  -----         
 0   time_stamp      35040 non-null  datetime64[ns]
 1   price           35040 non-null  float64       
 2   Status          35040 non-null  object        
 3   imbalance       35040 non-null  int64  

   

我在 model.T 中修改了 to_list() > to_dict() 但仍然面临同样的问题:

KeyError:在模型参数、集合和变量中定义 model.T 时,“无法将标量组件 'P' 视为索引组件”。

这里是系统报错的约束:

def revenue_positive(model,t):
        for t in model.T:
            return (model.C[t] * model.P[t]) >= 0
    
    model.positive_revenue = Constraint(model.T,rule=revenue_positive)

想不通...有什么想法吗? 更新 模型在某处删除不幸的 'quarter' 列后工作......在我将索引重命名为 quarter 之后。 它运行但我仍然得到负收入,所以限制目前似乎不起作用,它是这样写的:

def revenue_positive(模型,t): 对于 model.T 中的 t: return (model.C[t] * model.P[t]) >= 0

model.positive_revenue = Constraint(model.T,rule=revenue_positive)

我在这里错过了什么?感谢帮助,刚刚开始

欢迎来到本站。

您似乎遇到的问题是您没有将模型参数 model.P 构建为索引组件。我相信您可能希望它被您的集合索引 model.T.

当你在 pyomo 中创建索引参数时,你需要用一些 key:value 配对来初始化它,比如 python 字典。您可以通过 re-indexing 您的数据框从您的数据框中创建它,这样季度标签就是索引值。

警告:model.T 的构造和此 假设 季度名称 中没有重复项。

如果您有重复项(或收到警告),那么您需要执行其他操作。如果季度标签是唯一的,您可以这样做:

import pandas as pd
import pyomo.environ as pyo
df = pd.DataFrame({'qtr':['Q5', 'Q6', 'Q7'], 'price':[12.80, 11.50, 8.12]})
df.set_index('qtr', inplace=True)
print(df)

m = pyo.ConcreteModel()
m.T = pyo.Set(initialize=df.index.to_list())
m.price = pyo.Param(m.T, initialize=df['price'].to_dict())

m.pprint()

哪个应该让你:

     price
qtr       
Q5   12.80
Q6   11.50
Q7    8.12

1 Set Declarations
    T : Size=1, Index=None, Ordered=Insertion
        Key  : Dimen : Domain : Size : Members
        None :     1 :    Any :    3 : {'Q5', 'Q6', 'Q7'}

1 Param Declarations
    price : Size=3, Index=T, Domain=Any, Default=None, Mutable=False
        Key : Value
         Q5 :  12.8
         Q6 :  11.5
         Q7 :  8.12

2 Declarations: T price

为清楚起见编辑...

注意:

创建 pyomo 参数时的第一个参数是索引集。如果未提供,pyomo 假定它是一个标量。您缺少 set,如我的示例所示,并在此处用箭头突出显示::)

                     |
                     |
                     |
                     V
m.price = pyo.Param(m.T, initialize=df['price'].to_dict())

另请注意,您需要使用 dictionary 初始化 model.P,就像我在示例中所做的那样,not a列表。