How to declare params in pyomo?

Question:

I am having a difficult with pyomo’s params declaration. I have a np array like I declared bellow, but it appear this error: KeyError: "Index '0' is not valid for indexed component 'c'.

model = pyo.ConcreteModel()

V = range(20)

model.V = pyo.Set(initialize = V, doc = 'Set: clients and depots', within = pyo.NonNegativeIntegers)

c = np.zeros((len(V), len(V)))

model.c = pyo.Param(V, V, initialize = c, doc = 'Param: distances', within = pyo.NonNegativeReals)

ChatGPT said that I could make this:

c_dict = {(i, j): c[i][j] for i in V for j in V}
model.c = pyo.Param(V, V, initialize=c_dict, doc='Param: distances', within=pyo.NonNegativeReals)

But I don’t undestand very well why this. I already readed the documentation, but I didn’t undestand why I can’t declare in "initialize" key.

Asked By: Josa Ferreira

||

Answers:

The core issue is that multi-indexed things in pyomo are tuple-indexed like:

x[i, j, k, ...]

and if you have an n-dimensional array in basic python (list of lists) or n-dimensional numpy array, they are "layered" indexed (not sure if that is right term) like:

x[i][j][k]

So in your case, if you have a distance matrix in a matrix format of some kind, which is very natural, you have 2 choices: You can either convert it to a dictionary (which is tuple-indexed) or just use a helper function…something like:

import pyomo.environ as pyo
import numpy as np

model = pyo.ConcreteModel()

V = range(20)

model.V = pyo.Set(initialize = V, doc = 'Set: clients and depots', within = pyo.NonNegativeIntegers)

c = np.zeros((len(V), len(V)))

def helper(model, i, j):
    # convert from layered inex to tuple-indexed...
    return c[i][j]

model.c = pyo.Param(model.V, model.V, initialize = helper, doc = 'Param: distances', within = pyo.NonNegativeReals)

A couple notes…

If your distances are all zero (or if you have a sparse matrix), you can/should just use a default value in the construct to fill in the missing data or the whole thing (if all zero)

Also, you should use model.V for the indexing sets instead of just V. (See the changes I made in that part.)

Answered By: AirSquid
Categories: questions Tags: , ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.