Pyomo: Limit equations to variables in a relative position in the set as in GAMS

I am new to Pyomo (and Python). I have implemented a problem in GAMS and would like to do the same using Pyomo. I have a problem with an equation, which is depending on two consecutive time steps. More specifically, I define two equations: one which is true when the time steps are strictly greater than 1 (ramp) and another if not (ramp0). Below you can find the problem formulated in GAMS. It is there possible to define only one set and for each equation to define the range for which the equation is true, using “ord”. What would be the correct way to do this using Pyomo? I attached a possible approach I thought about but would be pleased to hear from experts. Thank you very much for your help.

Gams:

Set
t time periods /1*150/
(..)
Variable
p(t)
;
Equation
ramp(t)
ramp0(t)
;
ramp(t) $ ( ord(t) gt 1)..-RD*DeltaT=l=p(t)-p(t-1),
ramp0(t) $ ( ord(t) le 1)..-RD*DeltaT=l=p(t)-p0,

----------------------

# Creation of a Concrete Model
VRB = ConcreteModel()
# Sets
VRB.t=RangeSet(1,88,1)
VRB.t0=Set(VRB.t & RangeSet(1,1,1), within=VRB.t)
VRB.t1=Set(within=VRB.t)
VRB.p=Var(VRB.t,bounds=(0.0, 1.0))
VRB.limits=ConstraintList()
for t in VRB.t :
(…)
For t in VRB.t1
 VRB.limits.add (-RD*DeltaT <=p[t]-p[t-1])
For t in VRB.t0
VRB.limits.add (-RD*DeltaT <=p[t]-p0)

Hi @eglantine Can’t help with your question sorry, but I just set the GAMS code in a code block: simply indent each line with 4 spaces. This site accepts GFM (GitHub flavored markdown) but the Discourse software that drives the site started migrating to CommonMark plus table and other extensions in June 2017. I don’t know whether that process is complete or not. Robbie

Hi @eglantine,
actually, I do not think, that you need these ordered sets for pyomo.
In urbs, we have a set with our modeled time steps, which starts at 1. As we additionally have timeseries starting from 0 (with all values 0), we can then define e.g. the storage state via

def def_storage_state_rule(m, t, sit, sto, com):
return (m.e_sto_con[t, sit, sto, com] ==
m.e_sto_con[t-1, sit, sto, com] *
(1 - m.storage_dict['discharge'][(sit, sto, com)]) +
m.e_sto_in[t, sit, sto, com] *
m.storage_dict['eff-in'][(sit, sto, com)] * m.dt -
m.e_sto_out[t, sit, sto, com] /m.storage_dict['eff-out'][(sit, sto, com)] * m.dt)

Does that help you?

You can do:

model = pyomo.ConcreteModel()
model.timesteps = pyomo.Set([0, 1, 2, ... ], ordered=True) 

Inside rules you may use python if statements etc.:

    def rule(model, t):
        if t == model.timesteps.first(): 
            return pyomo.Constraint.Skip
        else: 
            return model.x[t] == model.x[t-1]  
     ...   

There is also a very good google list for pyomo questions, with quick responses (look for pyomo-forum on the internet).

1 Like

Thank you both for the help. I think the rule-based approach is the approach I was looking for.