Hello,

I have two different dynamic sets. I have iterations and in each iteration what I want to do is to choose one of the elements of each of the sets randomly and exchange them. How can I do this with Gams? I will be glad for your help, thanks

Hello,

I have two different dynamic sets. I have iterations and in each iteration what I want to do is to choose one of the elements of each of the sets randomly and exchange them. How can I do this with Gams? I will be glad for your help, thanks

Hi

You can use the uniform and round function to do stuff like this. Perhaps this helps (I am not quite sure what you want to do; an example to explain it would be better):

```
set i /1*10/, r(i);
r(i)$(round(uniform(1,11)) = i.val) = YES;
display r;
```

Renger

Hi Renger,

Thank u very much for replying.

Let me explain what I want to do with an example

Sets

i nodes /1*10/

N1(i) /3,5,7/

N2(i) /1,2,4,6,8,9,10/

We can assume that this is a facility location problem and N1 is the set of nodes at which I locate the facilities.

I am trying to code an algorithm and according to this algorithm at each iteration I will choose one element from N1 randomly and add to N2, and also choose one element from N2 randomly and add to N1

For example if the first element of the sets are chosen randomly then I am expecting to get

N1(i) /1,5,7/

N2(i) /3,2,4,6,8,9,10/

I will create N1 and N2 as dynamic sets

If I know that I am choosing 3 from N1 the I can say that

N1(‘3’)=no;

N2(‘3’)=yes;

ın fact ı am trying to find a way to code as N1(‘randomly selected element’)=no; etc…

Is there a practical way to be able to do this?

Thanks

Betul

Hi Betul

Here is a solution that works (it might not be the most elegant, but it works

```
set
i nodes /1*10/,
is /3,5,7/, ib /1,2,4,6,8,9,10/,
l /1*1000/;
parameter
vn1(i), vn2(i);
vn1("1") = 3;
vn1("2") = 5;
vn1("3") = 7;
vn2("1") = 1;
vn2("2") = 2;
vn2("3") = 4;
vn2("4") = 6;
vn2("5") = 8;
vn2("6") = 9;
vn2("7") = 10;
parameter cn1, cn2, k1, k2;
loop(l$(l.val < 10),
* Set the sets back to the original values
is(i) = NO;
ib(i) = NO;
is("3") = YES;
is("5") = YES;
is("7") = YES;
ib("1") = YES;
ib("2") = YES;
ib("4") = YES;
ib("6") = YES;
ib("8") = YES;
ib("9") = YES;
ib("10") = YES;
* Pick a random element of both sets by taking a random position
cn1 = floor(uniform(1,card(is) + 1));
cn2 = floor(uniform(1,card(is) + 1));
* Find the set element by using the parameter
loop(i$(i.val = cn2), k2 = vn2(i));
loop(i$(i.val = cn1), k1 = vn1(i));
* Add the elements to the sets
loop(i$(i.val = k2), is(i) = YES);
loop(i$(i.val = k1), ib(i) = YES);
* Remove the elements from the sets
loop(i$(i.val = k1), is(i) = NO);
loop(i$(i.val = k2), ib(i) = NO);
display is, ib;
);
```

Renger

Dear Renger,

I am really very glad for your help.

Thank you for the code, it works but unfortunately I recognized that I skipped to explain sth.

In each iteration I am trying to keep the sets updated.

For example

is /3,5,7/

ib /1,2,4,6,8,9,10/

in the first iteration I got

is /1,5,7/

ib /3,2,4,6,8,9,10/

now I would like to keep is and ib as

is /1,5,7/

ib /3,2,4,6,8,9,10/ to continue for the other iterations.

So I deleted the part

is(i) = NO;

ib(i) = NO;

is(“3”) = YES;

is(“5”) = YES;

is(“7”) = YES;

ib(“1”) = YES;

ib(“2”) = YES;

ib(“4”) = YES;

ib(“6”) = YES;

ib(“8”) = YES;

ib(“9”) = YES;

ib(“10”) = YES;

so I am able to keep the sets updated.

But I also have to keep the parameters vn1 and vn2 updated because the code is choosing the elements from the sets first given

Now in the loop I am trying to update the vn1 and vn2 at each iteration

If you have any idea about it, I will be very happy

Thank you

Regards

Betul

just add the following two lines at the end just before the end of the loop

```
vn1(i)$(ord(i) = cn1) = k2;
vn2(i)$(ord(i) = cn2) = k1;
```

Renger

It works just as I need.

Thank you very much for your time.

Regards

Betul