16.1 INTRODUCTION
The previous chapters have focused on the ability of GAMS to describe models. This chapter will describe the various programming features available in GAMS to help the advanced user.
The various programming flow control features discussed in this chapter are
• Loop Statement
• If-Else Statement
• For Statement
• While Statement
Each of these statements will be discussed in detail in the following sections.
16.2 THE LOOP STATEMENT
The loop statement is provided for cases when parallel assignments are not sufficient. This happens most often when there is no analytic relationship between, for example, the values to be assigned to a parameter. It is, of course, also useful to have a looping statement for general pro-gramming - for example, the production of reports with the put statement.
16.2.1 THE SYNTAX
The syntax of the loop statement is,
loop(controlling_domain[$(condition)], statement {; statement}
) ;
If the controlling_domain consists of more than one set, then parentheses are required around it.
The loop statement causes GAMS to execute the statements within the scope of the loop for each member of the driving set (s) in turn. The order of evaluation is the entry order of the labels.
A loop is thus another, more general, type of indexed operation. The loop set may be dollar-controlled and does not need to be static or nested. Loops may be dollar-controlled by more than one set.
One cannot make declarations or define equations inside a loop statement It is illegal to modify any controlling set inside the body of the loop.
PROGRAMMING FLOW CONTROL FEATURES 152
16.2.2 EXAMPLES
Consider a hypothetical case when a growth rate is empirical:
set t / 1985*1990 /
parameter pop(t) / 1985 3456 /
growth(t) / 1985 25.3, 1986 27.3, 1987 26.2 1988 27.1, 1989 26.6, 1990 26.6 /;
The loop statement is then used to calculate the cumulative sums
loop(t, pop(t+1) = pop(t) + growth(t) ) ;
in an iterative rather than a parallel way. In this example there is one statement in the scope of the loop, and one driving, or controlling, set.
A loop is often used to perform iterative calculations. Consider the following example, which uses finds square roots by Newton’s method. This example is purely for illustration - in practice, the function sqrt should be used. Newton’s method is the assertion that if x is an approximation to the square root of v, then (x+v/x)/2 is a better one
set i "set to drive iterations" / i-1*i-100 /;
parameter value(i) "used to hold successive approximations" ; scalars
target "number whose square root is needed" /23.456 / sqrtval "final approximation to sqrt(target)"
curacc "accuracy of current approximation"
reltol "required relative accuracy" / 1.0e-06 / ; abort$(target <= 0) "argument to newton must be positive", target;
value("i-1") = target/2 ; curacc = 1 ; loop(i$(curacc > reltol),
value(i+1) = 0.5*(value(i) + target/value(i));
sqrtval = value(i+1);
curacc = abs (value(i+1)-value(i))/(1+abs(value(i+1))) ) ;
abort$(curacc > reltol) "square root not found"
option decimals=8;
display "square root found within tolerance", sqrtval, value;
The output is:
---- 18 square root found within tolerance
---- 18 PARAMETER SQRTVAL = 4.84313948 final approximation to sqrt(target) ---- 18 PARAMETER VALUE used to hold successive approximations i-1 11.72800000, i-2 6.86400000, i-3 5.14062471, i-4 4.85174713 i-5 4.84314711, i-6 4.84313948, i-7 4.84313948
16.3 THE IF-ELSEIF-ELSE STATEMENT
The if-else statement is useful to branch conditionally around a group of statements. In some cases this can also be written as a set of dollar conditions, but the if statement may be used to make the GAMS code more readable. An optional else part allows you to formulate traditional if-then-else constructs.
16.3 THE IF-ELSEIF-ELSE STATEMENT 153
16.3.1 THE SYNTAX
The syntax for an if-elseif-else statement is:
if (condition, statements;
{elseif condition, statements } [else statements;]
);
where condition is a logical condition.
One cannot make declarations or define equations inside an if statement.
16.3.2 EXAMPLES
Consider the following set of statements
p(i)$(f <= 0) = -1 ;
They can be expressed using the if-elseif-else statement as
if (f <= 0,
The body of the if statement can contain solve statements. For instance, consider the follow-ing bit of GAMS code:
The following GAMS code is illegal since one cannot define equations inside an if statement.
if (s gt 0,
eq.. sum(i,x(i)) =g= 2 ; );
The following GAMS code is illegal since one cannot make declarations inside an if statement.
PROGRAMMING FLOW CONTROL FEATURES 154
if (s gt 0,
scalar y ; y = 5 ; );
16.4 THE WHILE STATEMENT
The while statement is used in order to loop over a block of statements.
16.4.1 THE SYNTAX
The syntax of the while statement is:
while(condition, statements;
);
One cannot make declarations or define equations inside a while statement.
16.4.2 EXAMPLES
One can use while statements to control the solve statement. For instance, consider the following bit of GAMS code that randomly searches for a global optimum of a non-convex model:
scalar count ; count = 1 ; scalar globmin ; globmin = inf ; option bratio = 1 ;
while((count le 1000),
x.l(j) = uniform(0,1) ;
solve ml using lp minimizing obj ; if (obj.l le globmin,
globmin = obj.l ; globinit(j) = x.l(j) ; ) ;
count = count+1 ; ) ;
In this example, a non-convex model is solved from 1000 random starting points, and the global solution is tracked. The model [PRIME] from the model library illustrates the use of the while statement through an example where the set of prime numbers less than 200 are generated The following GAMS code is illegal since one cannot define equations inside a while state-ment.
while (s gt 0,
eq.. sum(i,x(i)) =g= 2 ; );
The following GAMS code is illegal since one cannot make declarations inside a while state-ment.
while(s gt 0,
scalar y ; y = 5 ; );
16.5 THE FOR STATEMENT 155
16.5 THE FOR STATEMENT
The for statement is used in order to loop over a block of statements.
16.5.1 THE SYNTAX The syntax is:
for (i = start to|downto end [by incr], statements;
);
Note that i is not a set but a parameter. Start and end are the start and end, and incr is the increment by which i is changed after every pass of the loop.
One cannot make declarations or define equations inside a for statement.
The values of start, end and incr need not be integer. The start and end values can be positive or negative real numbers. The value of incr has to be a positive real number.
16.5.2 EXAMPLES
One can use for statements to control the solve statement. For instance, consider the follow-ing bit of GAMS code that randomly searches for a global optimum of a non-convex model:
scalar i ;
scalar globmin ; globmin = inf ; option bratio = 1 ;
for (i = 1 to 1000,
x.l(j) = uniform(0,1) ;
solve ml using nlp minimizing obj ; if (obj.l le globmin,
globmin = obj.l ; globinit(j) = x.l(j) ; );) ;
In this example, a non-convex model is solved from 1000 random starting points, and the global solution is tracked.
The use of real numbers as start, end and the increment can be understood from the fol-lowing example,
for (s = -3.4 to 0.3 by 1.4, display s ;
);
The resulting listing file will contain the following lines,
---- 2 PARAMETER S = -3.400 ---- 2 PARAMETER S = -2.000 ---- 2 PARAMETER S = -0.600
Notice that the value of s was incremented by 1.4 with each pass of the loop as long as it did not exceed 0.3.
The following GAMS code is illegal since one cannot define equations inside a for statement.
PROGRAMMING FLOW CONTROL FEATURES 156
for (s = 1 to 5 by 1,
eq.. sum(i,x(i)) =g= 2 ; );
The following GAMS code is illegal since one cannot make declarations inside a for statement.
for (s=1 to 5 by 1, scalar y ; y = 5 ; );