searching string in set

Hi all,

Let’s suppose i have a set X = \y1 y2 y3 … z1 z2\ and a variable w(X) = \y1 10, y2 20, y3 30, … , z1 40, z2 50
Is there an easy way of summing the values for all the elements of w(X) that have the string “y” in their name?

Thanks in advance!

Doing set member ship based on the name of a label is not what you should do in GAMS. We make this difficult on purpose, because that is a fragile thing. Better be explicit about it:

set X /y1*y3, z1* z2/, Y(X) / y1*y3 /;
Parameter w(X)  /y1 10, y2 20, y3 30, z1 40, z2 50/;
Scalar ysubsum; ysubsum = sum(Y, w(Y)); display ysubsum;

The ord function (https://www.gams.com/latest/docs/UG_Parameters.html#UG_Parameters_StringFunctions) allows to access the ASCII code of a string for particular positions, so the following code calculates the set Y based on the first character being a ‘y’ or a ‘Y’:

set X /y1*y3, z1* z2/, Y(X);
Parameter w(X)  /y1 10, y2 20, y3 30, z1 40, z2 50/;
loop(X, Y(X) = (ord(X.tl,1)=ord('y',1)) or (ord(X.tl,1)=ord('Y',1)));
Scalar ysubsum; ysubsum = sum(Y, w(Y)); display Y,ysubsum;

-Michael

Thanks Michael, this was very helpful!

I have a different problem.

I have the following code:

set Tid /2000*2020/;
singleton set FinalYear /2017/;
singleton set StatBank /2017/;

if (FinalYear < StatBank,
	loop( ...);
);

I have an error when starting “if” condition.
I would like to “compare” the years (elements) of these two singleton sets, and if they are the same I want to do the loop statement.

Hi, to be able to compare them I think they should be defined as parameters.
Another possibility is to use auxiliary parameters.
To search for a string in a set, I usually use the “sameas” command.
Bye!

Yes, thank you ! I used “sameas” command :slight_smile:

Another think is that I want to loop over elements in a set in descending order. For example:

set tid /2000*2014/;
loop(tid$(2014, 2013, ..., 2000),
	"an equation";
);

Hi, I think that order doesn’t matter when you defining an equation.

set tid /2000*2014/;

equationx(tid)$condition(tid)… “an equation”

I would like to make a loop from 2014 to 2000 - in ascending order, and not from 2000 to 2014.

I quickly think that it can be something like this:

set tid /2000*2014/;
parameter
p
;
loop(tid,
p=2014-(ord(tid) -1)
display p;
);

Or, if you need to use the set tid:

set tid /2000*2014/;
alias(tid,tidp)
parameter
p
;
loop(tidp,
loop(tid$(ord(tid) eq card(tid) - (ord(tidp)-1)),
p=ord(tid);
display p;
););

I have sth like this (se attachment). And I tried to apply your code, but it says: “Lags are not allowed on maps”.
rrrr.JPG

In your code tac is a subset not a set… i think this is the problem