Subsets in AMPL

4,248 views
Skip to first unread message

David Rey

unread,
Oct 6, 2011, 12:52:20 PM10/6/11
to AMPL Modeling Language
Hello,

I would like to know how to declare subsets in AMPL and, if possible,
how to generate them in a loop.

Say I have a set X :={1,2,3,4} of four elements and a set of subsets
of X, Y :={(1,2),3,4} of three elements. Suppose t[x] are the decision
variables of my model, my objective is to write a series of
constraints such as:

For all y in Y : sum{x in y} t[x] >= ...;

which would yield the following constraints in my example:

t[1] + t[2] >= ...;
t[3] >= ...;
t[4] >= ...;

However, as x is an element of y which is an element of Y, I can't
manage to get the right formulation. I tried to declare y as an
"indexed" subset:
param i {1..3};
set y[i] within X;

but it does not seem to work this way, could you help understand the
correct syntax for doing this?

Thank you for your help,
David Rey.

Robert Fourer

unread,
Oct 8, 2011, 10:07:49 PM10/8/11
to am...@googlegroups.com
A collection of sets can be declared to be indexed over a set, in the same
way as a parameter but with the statement "set" rather than "param". For
instance:

set X;
param I;
set Y {1..I} within X;

Then the data would be:

set X := 1 2 3 4 ;
param I := 3 ;

set Y[1] := 1 2 ;
set Y[2] := 3 ;
set Y[3] := 4 ;

And the constraint could be:

subj to constr {i in 1..I}:
sum {j in Y[i]} t[j] >= ... ;

Bob Fourer
4...@ampl.com

David Rey

unread,
Oct 11, 2011, 6:01:41 AM10/11/11
to AMPL Modeling Language
Thank you very much, it works perfectly !

Cheers,
David Rey.

Jennifer Arellana Guzman

unread,
Nov 4, 2021, 8:05:48 PM11/4/21
to AMPL Modeling Language
Dear Fourer,
I am performing something similar to what you explain in this answer but I am performing it with a For loop, I set up the following:
- In the .mod file:
param NJ;
set O;
set Osub {1..NJ} within O;

- In the .dat file:
set O :=   
O1
O2
O3
O4
O5
O6
O7
O8
O9
O10
O11
O12
O13
O14
O15
O16
O17
O18
O19
O20
O21
;

set Osub[1] := O1;
set Osub[2] := O2;
set Osub[3] := O3;
set Osub[4] := O4;
set Osub[5] := O5;
set Osub[6] := O6;
set Osub[7] := O7;
set Osub[8] := O8;
set Osub[9] := O9;
set Osub[10] := O10;
set Osub[11] := O11;
set Osub[12] := O12;
set Osub[13] := O13;
set Osub[14] := O14;
set Osub[15] := O15;
set Osub[16] := O16;
set Osub[17] := O17;
set Osub[18] := O18;
set Osub[19] := O19;
set Osub[20] := O20;
set Osub[21] := O21;

param NJ := 21;

- And in the .run file:
option solver cplex;

param FLPCA{1..NJ} default 0;
for {i in 1..NJ}{
    display Osub[i];
    let O := Osub[i];
    #let O := {i in 1..NJ} Osub[i];
    #let O := {i in 1..Osub};
    #let Osub := {o in O: (iter div 2**(ord(o)-1))) mod 2 = 1};
    solve;
    let FLPCA[i] := FCN;
    display FLPCA;
}

But when I give it run I get this error starting from iteration 2:

CPLEX 20.1.0.0: optimal integer solution; objective 2897720204
1141 MIP simplex iterations
0 branch-and-bound nodes
FLPCA [*] :=
1  2897720204.37
;
Error at _cmdno 10 executing "display" command
(file D:\..\Run_Sin_PowerSet_Benef_D2.run, line 9, offset 470):
error processing error set Osub[2]:
    Osub[2] contains O2, which is not
    within O;
Error at _cmdno 10 executing "display" command
(file D:\..\Run_Sin_PowerSet_Benef_D2.run, line 9, offset 470):
     Osub[3] contains O3, which is not
    within O;
:

This is repeated with the other 18 runs that are needed. But what I see is that if it solves the first iteration which is when Osub[1] = O1.

I have tried to solve it in different ways but I can't identify where I am going wrong. Any help would be appreciated.

Thank you for your attention and I remain attentive.

Regards!

Davi Doro

unread,
Nov 5, 2021, 9:34:13 AM11/5/21
to AMPL Modeling Language
The command let O := Osub[i] inside your for-loop changes the value of O at every iteration. It starts with O1, O2, O3 ... O21, but then, in the first iteration, O becomes a set with a single entry, i.e., O1. Then, in the second iteration, when you try to display Osub[2] it returns an error because O2 is no longer a subset of O. The same happens in subsequent iterations.

Maybe if you give more information on what you are trying to accomplish we can help you solve the problem.

Jennifer Arellana Guzman

unread,
Nov 5, 2021, 12:49:08 PM11/5/21
to AMPL Modeling Language
I am solving a profit maximization model and I have that the set O is the set of all players, what I want is that this model is solved for each of the players that are in this set and at the end I get a matrix that has the result of the objective function of each player. With what you told me I made this change to the loop:
- I added to the .dat file:
set Oaux :=   

O1
O2
O3
O4
O5
O6
O7
O8
O9
O10
O11
O12
O13
O14
O15
O16
O17
O18
O19
O20
O21
;
- I added to the .mod file:
set Oaux;
- And to the .run file I made this change:

option solver cplex;

param FLPCA{1..NJ} default 0;
for {i in 1..NJ}{
    display Osub[i];
    let O := Osub[i];
    solve;
    let FLPCA[i] := FCN;
    display FLPCA;
    let O := Oaux; #This right here.
}

However, now I get another error, which is as follows:
Error at _cmdno 13 executing "solve" command.
(file D:..Benef_D2.run, line 11, offset 509):
error processing param CT_oa:
    23 invalid subscripts discarded:
    CT_oa['O1','A1']
    CT_oa['O1','A2']
    CT_oa['O1','A3']
    and 20 more.
Error at _cmdno 13 executing "solve" command
(file D:..Benef_D2.run, line 11, offset 509):
error processing param CT_oc:
    4 invalid subscripts discarded:
    CT_oc['O1','C1']
    CT_oc['O1','C2']
    CT_oc['O1','C3']
    and 1 more.
Error at _cmdno 13 executing "solve" command
(file D:..Benef_D2.run, line 11, offset 509):
error processing param V_otp:
    10 invalid subscripts discarded:
    V_otp['O1','T1','P1']
    V_otp['O1','T1','P2']
    V_otp['O1','T1','P3']
    and 7 more.
Error at _cmdno 13 executing "solve" command
(file D:..Benef_D2.run, line 11, offset 509):
error processing var Ship_oa:
    no value for CT_oa['O2','A1']'

I identify that all the parameters that had a subindex of the set O appear as if they were empty, like this:
ampl: display CT_oa;
CT_oa; #empty

ampl: display CT_oc;
CT_oc; #empty

ampl: display V_otp;
V_otp; #empty

Do you have any idea how to fix this other error? Any help would be appreciated.

Greetings!

Davi Doro

unread,
Nov 5, 2021, 1:37:46 PM11/5/21
to AMPL Modeling Language
I believe one of the problems in your code is that let O := Oaux happens at the end of each iteration, but at the begining of each iteration you make another assignment let O := Osub[i], which discards the previous one. So your current code is basically the same as the previous one, except that now it can display Osub[i], because O is always equals to Oaux at that point.

However, even if you move let O := Oaux to another place, I think the bigger problem is that your parameters and variables depend on the set O, to which you are assigning a single value at each iteration, but your model expects it to have entries that it does not have.

If your model is not private, it would help if you could share the entire files, because the error concerns parameters and variables you have not shared.

But if that's all you can share, I suggest that you consider structuring your loop somewhat like this:

for {i in 1..NJ} {
    model "model.md";
    data "data.dat";
    # do relevant changes
    solve;
}

That way you will always "start fresh" at each iteration, and only change a few things here and there.

More info on the model and data commands: https://pifop.com/help/ampl_basic_commands.html

Davi Doro

unread,
Nov 5, 2021, 1:49:59 PM11/5/21
to AMPL Modeling Language
I'm sorry, model should not be inside the loop, and I forgot to reset the data:

model "model.md";

for {i in 1..NJ} {
    reset data;
    data "data.dat";
    # do relevant changes
    solve;
}

Jennifer Arellana Guzman

unread,
Nov 5, 2021, 2:48:15 PM11/5/21
to AMPL Modeling Language
I understand, this does work but because we reset the data in the loop it causes that the results of each iteration cannot be saved in "FLPaux", is there a way to save the results of each iteration?

Davi Doro

unread,
Nov 5, 2021, 5:39:02 PM11/5/21
to AMPL Modeling Language
Yes, instead of reset data you can use update data. The update command allows you to reassign values in a data section without discarding old data:

model "model.md";
param FLPCA{1..NJ};

for {i in 1..NJ} {
    update data;
    data "data.dat";
    # do relevant changes
    solve;
    let FLPCA[i] := FCN;
    display FLPCA;
}

Jennifer Arellana Guzman

unread,
Nov 6, 2021, 11:43:58 AM11/6/21
to AMPL Modeling Language
Thank you very much! this worked just as I expected!
Reply all
Reply to author
Forward
0 new messages