potentially unwanted side effects of empty(messages)

41 views
Skip to first unread message

Achim Gädke

unread,
May 20, 2014, 1:05:40 PM5/20/14
to gama-p...@googlegroups.com
Hi there!

I'm simulating a call centre where 2 "callCentreAgent"s serving 20 "helpless" customers using the communicating skill. (full model appended, using most recent GAMA1.6.1)

To determine which call centre agent gets the call, I use these lines of code:

callCentreAgent theAgent <- nil;
theAgent <- one_of(callCentreAgent where empty(each.messages));
if theAgent = nil {
theAgent <- one_of(callCentreAgent);
}

watching out for free agents and then using a random one.

Sadly, when using the where empty clause only the last two messages are worked on, see output.
helpless0 origin: startCall: contacting callCentreAgent1
helpless1 origin: startCall: contacting callCentreAgent0
helpless2 origin: startCall: contacting callCentreAgent0
helpless3 origin: startCall: contacting callCentreAgent0
helpless4 origin: startCall: contacting callCentreAgent0
helpless5 origin: startCall: contacting callCentreAgent1
helpless6 origin: startCall: contacting callCentreAgent1
helpless7 origin: startCall: contacting callCentreAgent0
helpless8 origin: startCall: contacting callCentreAgent0
helpless9 origin: startCall: contacting callCentreAgent1
helpless10 origin: startCall: contacting callCentreAgent1
helpless11 origin: startCall: contacting callCentreAgent1
helpless12 origin: startCall: contacting callCentreAgent0
helpless13 origin: startCall: contacting callCentreAgent1
helpless14 origin: startCall: contacting callCentreAgent1
helpless15 origin: startCall: contacting callCentreAgent1
helpless16 origin: startCall: contacting callCentreAgent1
helpless17 origin: startCall: contacting callCentreAgent1
helpless18 origin: startCall: contacting callCentreAgent1
helpless19 origin: startCall: contacting callCentreAgent0
helpless18 origin: pickUpReslut done with callCentreAgent1
helpless19 origin: pickUpReslut done with callCentreAgent0

When I remove the where empty line i.e. only random scheduling is done, the service works well.

So, I find that the check whether the messages queue is empty removes the messages from the mailbox "messages". But I would guess the empty check should not change the mailbox.

The way the mailbox is implicitly emptied is explained at https://code.google.com/p/gama-platform/wiki/communicating_skill16, message data type:
unread, bool, true if the message has not yet been read and false otherwise. A message is considered as already read if its "content" field is accessed. An already read message will be automatically removed from the mailbox of agent, the modeler thus doesn't have to manually removed the already read messages.)

Does anyone know how to check the messages container without changing it?

Cheers, Achim
callCentreTest.gaml

Benoit Gaudou

unread,
May 22, 2014, 3:33:59 AM5/22/14
to Duc An Vo, gama-p...@googlegroups.com, Achim Gädke
Hi An,

If I remember well, for the JTD 2013 model, I used the FIPA extension and also tested the emptiness of the messages / informs / requests lists with : 

reflex get_messages when: ! empty(requests) {

..... 

}


I do not remember that it empties the associated lists.

Do you think there is some change in the extension ?


Thank you in advance


Benoit 




--
You received this message because you are subscribed to the Google Groups "GAMA" group.
To unsubscribe from this group and stop receiving emails from it, send an email to gama-platfor...@googlegroups.com.
To post to this group, send email to gama-p...@googlegroups.com.
Visit this group at http://groups.google.com/group/gama-platform.
For more options, visit https://groups.google.com/d/optout.

Duc An Vo

unread,
May 22, 2014, 4:22:31 AM5/22/14
to gama-p...@googlegroups.com
Hi,

With the "communicating" skill, we have a set of list built-in variables which represent the mailbox of an agent.

For example, "messages" is a list containing all the (not yet read) messages of an agent.
We all so have "informs", "requests", ... lists containing all (not yet read) messages having "inform", "request", ... as performative.
"informs", "requests", ... are just filters of "messages" which retain only messages of "messages" with the corresponding performative.

Please refer to the "built-in variables" section at https://code.google.com/p/gama-platform/wiki/communicating_skill16 for a detail description. 

We can apply list operators (e.g., length, empty, ...) on these built-in variables without changing their content. But as soon as we access a message's content (i.e., write "a_message.content" in GAML), the message will be automatically removed from the agent's mailbox at the end of the current simulation step.

Cheers,
An.


--

Benoit Gaudou

unread,
May 22, 2014, 4:40:18 AM5/22/14
to gama-p...@googlegroups.com
Hi An,

Thanks for your answer.
I made deeper test (cf. attached model).

Result : 
 - when we apply a list operator (length or empty) on built-in messages or informs listn it does not alter them
- BUT when we appply from another agent (length(first(callCentreAgent).informs) in the attached model), the list is emptied.

I do not know whether it is a feature...
Note that I agree that from a modeling point of view it is not a way to do... 

Benoit
TestCommunicating.gaml

Duc An Vo

unread,
May 22, 2014, 5:10:47 AM5/22/14
to gama-p...@googlegroups.com
Hi,

@Achim Gadke: After reading your code, I believe that the GAML implementation isn't really compatible which what you want to implement! :) 
I've just re-written a little bit your model. Please see the "callCentreTest_modified.gaml" model in the attachment. I hope that this might be what you intend to implement!

Concerning you original implementation, in the "startCall" reflex of the "helpless" species, all 20 "helpless" agents always try to contact one of the two "callCentreAgent" agents.
But in the "receivingRequest" reflex of "callCentreAgent" species, you only answer one "helpless" agent. This explains why we see only two responses in the console output (as we have two "callCentreAgent" agents).


@Benoit: I think the access to the "mailbox" lists are consistent whether we are either inside or outside a communicating agent. Please have a look at the "TestCommunicating_modified.gaml" model in the attachment.

Cheers,
An.


callCentreTest_modified.gaml
TestCommunicating_modified.gaml

Benoit Gaudou

unread,
May 22, 2014, 5:37:43 AM5/22/14
to gama-p...@googlegroups.com
Hi An,

I was wondering why the result is very différent when I put : 

reflex access_outside when: cycle > 1 {

and 

reflex access_outside when: cycle = 1 {

(Actually the list of message seems to have been partially emptied in the sceond case)

Benoit 

Achim Gädke

unread,
May 22, 2014, 5:47:13 AM5/22/14
to gama-p...@googlegroups.com

Hi there!

Thanks for all the input.

The modified model takes out the central aspect of a call centre, the queuing of communication. The modified code sends only one message.

As the implementation of 'mailbox'/messages as a container implies, communication might happen simultaneously (multiple conversations at once) or the sender has to wait till the receiver is able to answer or will postpone communicating with certain senders. I think this is an everyday aspect of communication.

Yesterday I tried out different strategies to circumvent this problem, but all failed when testing them with a heavy workload (i.e. provoking the simultaneous starting/queueing and ending conversations). Normally these situations happen accidentally - and from time to time my agents got stuck. In the examples supplied I make the overload the rule to demonstrate the problems.

Please refer to https://code.google.com/p/gama-platform/issues/detail?id=1035 for another example of the same issue - it is not connected to empty or length, but must be connected to the internal adding/removing process.

In that example, one can easily crank up the workload and see that it starts failing when messages are added by start_conversation to a non-empty queue from which messages are removed by end_conversation...

Cheers, Achim

Duc An Vo

unread,
May 22, 2014, 5:47:26 AM5/22/14
to gama-p...@googlegroups.com
Hello Benoit,

When you put "cycle = 1", the "access_outside" is only executed one time (when cycle = 1).

And when we are in "cycle = 1", the sent message (from the "helpless" agent) has not yet arrived in the mailbox of the "callCentreAgent" agent.
Thus, logically, we don't see them yet.

A message sent from the "helpless" agent in cycle 1 will be received by the "callCentreAgent" from the beginning of cycle 2.
It takes a simulation cycle to send a message! :)

Cheers,
An.

Benoit Gaudou

unread,
May 22, 2014, 5:53:48 AM5/22/14
to gama-p...@googlegroups.com
Hi An, 

I understand, but when you have : reflex access_outside when: cycle >= 1 { .... 

You still have only 1 message in the agents inbox.
(in addition, even when I put cycle = 1, the display from inside should show 4 elements in the list and not only one)

Benoit 

Duc An Vo

unread,
May 22, 2014, 6:17:51 AM5/22/14
to gama-p...@googlegroups.com
Hi Benoit,

I don't understand why we should have 4 elements in the list? In this case, one "helpless" agent sends one "inform" message to one "callCentreAgent" agent when cycle = 1.

I attach again the model. Could you please have a look at it?

Cheers,
An.
TestCommunicating_modified.gaml

Benoit Gaudou

unread,
May 22, 2014, 6:21:31 AM5/22/14
to gama-p...@googlegroups.com
Hi An,
OK my bad..... 
Actually I create  4 agents helpless ... (create helpless number: 4;
Reply all
Reply to author
Forward
0 new messages