Search code examples
optimizationsyntaxampl

Syntax for nested products and sums in AMPL optimization function


I'm having trouble indexing over a set. For some reason, I am getting a syntax error for the square bracket inside my sum for sum {i in {1..n_paths}} P[i];.

I'm able to display the set {i in {1..n_paths}}, and P[1] or any other legitimate i, but I'm not formatting the sum expression correctly somehow.

ampl: param n_paths;
ampl: set P {1..n_paths};
ampl: display sum {i in {1..n_paths}} P[i];

syntax error
context:  display sum {i in {1..n_paths}}  >>> P[ <<< i];

Solution

  • In your example, P is an an indexed collection of sets, which means that each P[i] is itself a set. For example:

    reset;
    param n_paths := 2;
    set P{1..n_paths};
    
    data;
    set P[1] := 1 2 5;
    set P[2] := 6 5 1;
    

    Here, display P[1]; returns set P[1] := 1 2 3;.

    If I try evaluating sum{i in 1..n_paths} P[i], I'm asking AMPL to add the set {1,2,3} to the set {6,5,1}, and the sum of two sets isn't defined. If I want to add up all the members of P[1] through P[n_paths] then I need a double sum:

    display sum{i in 1..n_paths} sum{j in P[i]} j;
    # caution: this will fail if we have non-numbers in our sets
    

    This returns 20: 1+2+5 from P[1] added to 6+5+1 from P[2].

    I could also merge the sets before summing:

    display sum{j in union{i in 1..n_paths} P[i]} j;
    

    Because union discards the duplicated values, this ends up summing 1, 2, 5, and 6 to get 14.