?
Solved

Waiting room sim. program help.

Posted on 2005-02-26
5
Medium Priority
?
301 Views
Last Modified: 2011-09-20
I'm trying to write a simulation with some statistical/metric information. The simulation goes as follow. It's a waiting room simulation. There will be one entrace will ppl wait in line to be seated in a room and en exit door when people to go the doctor's room (enter door and exit door will be at opposite end of this system. The waiting room will have about 10 chairs (two rows of five chairs each). When the ppl waiting in line goes into the waiting room, they look for an empty chair to sit randomly. If there are no empty seats, they will continue to wait until there's an empty seat and sit. Once everyone in line (queue) have all been in the waiting room, sat down, and leave. The system of the simulation ends.

Some of my state variables:
# of people waiting to be serve.
# of seats.
-arrival rate of people entering
-Range of how long ppl sit in seconds.
-Rate at which exit door will allow the people to leave (in seconds).

Each user waiting in line (queue) to find a sit will be assigned a random number (the seat). They will have time associated with them to from entering the door to finding a seat, the time they have seat, and the time from getting off the seat to exit.

Some data I want to keep track of:

1) Time each person spent in the system (waiting in line and seated),
2) # of ppl in entrance and exit queue, number of cars "seated"
3) average time in each queue,
4) average time a car is parked, etc.

I know I can write a queue of nodes. The queue will contain number of people waiting in line to be seated, with nodes containing info. about a user time spent waiting in line, time to get to the seat, time seated, time to leave, and the total time in the system.

- How would I write one when all the seats are full and the user has to wait? ex. "if seats are full, then user time increase. when one seat chair becomes empty, user takes a seat and the time gets recorded, etc, etc"?

Can someone help me with the pseudo-code and ideas on this, and especially help me with how to keep track of the data (1-4)?
0
Comment
Question by:identityless
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 3
5 Comments
 
LVL 1

Expert Comment

by:ricola
ID: 13413054
Hi do you need to come up with your program or ur main concern is just the datas and simulation ? If it is the later maybe u can try those simulation softwares that are available online such as Arena ? It will simulate the datas by the distribution models that are tagged to the entities..
0
 
LVL 7

Expert Comment

by:aib_42
ID: 13417133
One approach is using a global 'time':

unsigned long seconds = 0;

Have a "think function" for every 'intelligent' object:

/* NOTE: I'm using the '::' notation somewhat generally, this is pseudo-code */
Chair::think(unsigned long time)
{
    if (time >= Chair::GetLastSeatingTime() + Chair::MaximumSeatingTime) {
        Person = Chair::GetSittingPerson();
        Person::StandUp();
    }
}

and call the think() function for every intelligent object every second:

for (int i=0; i<=120; ++i) /* Run the simulation for 2 minutes */
    for (each object)
        object.think(i);

(Note how >= for comparing time is really unnecessary since every think function will be called every second)

Another example:

Person::think(unsigned long time)
{
    if (timeLastSatDown - time == 900) /* When I've sat for 15 minutes... */
        Person::GotBored(); /* ...I get bored */
}

Keeping track of data is easy this way, when you process the whole thing one frame at a time.
0
 

Author Comment

by:identityless
ID: 13422844
How would I find the avg. time each person spend in the queue (line)? I will have a queue for the waiting line and I know that the last person will take a longer time than the eariler people. How would I give a pseduo-code for the 1st person in the queue having a short waiting time and then in the end, the last person has a longer waiting time? For the avg. waiting time, I just add the total number of waiting time for all persons divided by number of people waited in the total system, correct?

- Assuming time when a person enters the waiting room, all the seats are occupied. I suppose a object.UserSeatingTime() increases until a space is available, correct? This is where I'm stuck on the coding part where the seats are full (assuming the people take a long time to seat) and a new user spents time looking for a seat. Can you help me with this part?

- Another problem I have is, only one person is allow to leave at a time (other people may be ahead). How would I prevent collison in timing?

Thanks!
0
 
LVL 7

Expert Comment

by:aib_42
ID: 13433598
>For the avg. waiting time, I just add the total number of waiting time for all persons divided by number of people waited in the total system, correct?

That is the definition of "average" :).

>I suppose a object.UserSeatingTime() increases until a space is available, correct?
UserSeatingTime() would increase for every frame that the user would be sitting:

object.Think() /* called every frame */
{
    seatingTime++;
}

Or, you could just record the frame # they sat down on and the one they stood up on, the difference would give the number of frames they've been sitting.

>- Another problem I have is, only one person is allow to leave at a time (other people may be ahead). How would I prevent collison in timing?

Very simple when you work with single frames and think functions:
person.Think()
{
    if (I have to leave)
        IWantToLeave = true;

    if (IWantToLeave == true)
        if (exitQueueFull == false))
            leave...
        else
            can't leave...
}

The good thing about running a simulation frame by frame is that you don't run into synchronization problems. Here is an example:

One person has sat down on frame #4 and will want to leave after sitting for 6 frames.
Another person has sat down on frame #5 and will want to leave after 5 frames.
Only one person can be leaving at any given time, a person takes 3 frames to leave.
It is frame #10, both persons want to leave at this time. Both their think functions are called, in a certain order:

Person1.think() {
    if (sitStart + sitMax == frame) /* 4+6=10 so this will eval to true */
        Person1.wantToLeave = true;
}

Person2.think() {
    if (sitStart + sitMax == frame) /* 5+5=10 so this will eval to true */
        Person2.wantToLeave = true;
}

/* At this point, both people want to leave */

Person2.thinkLeave() { /* second think function, you can have as many as you want */
    if (Person2.wantToLeave) { /* evals to true, was set in the previous think function */
        if (exitQueue.Full()) { /* false, noone leaving yet */
            /* do nothing */
        } else {
            exitQueue.Add(Person2); /* Ahh, we can leave now */
        }
    }
}

Person1.thinkLeave() {
    if (Person2.wantToLeave) { /* true, was set in the previous think function */
        if (exitQueue.Full()) { /* sadly, false, because Person2 was added to the queue in Person2.thinkLeave() */
            /* do nothing */
        } else {
            exitQueue.Add(Person2);
        }
    }
}

Can you see how there would never be a collision unless Person1.thinkLeave() and Person2.thinkLeave() were called at the exact same time? For there to be a collision, you would have to use multithreading, but our current implementation waits for one person to finish thinking before calling another one:

for(i=0; i<MAX_PERSONS; i++) {
    Person[i].think();
    Person[i].thinkLeave();
}

or

/* Stage 1 */
for(i=0; i<MAX_PERSONS; i++)
    Person[i].think();

/* Stage 2 */
for(i=0; i<MAX_PERSONS; i++)
    Person[i].thinkLeave();

(Actually, using two think functions is redundant, you could merge the functions and still not get any collisions.)
0
 
LVL 7

Accepted Solution

by:
aib_42 earned 1000 total points
ID: 13433738
How about a more general approach?

Person.Think()
{
    if (Person.state == WAITING_TO_SEAT) {

        if (seats are available)
            Person.sit();
        else
            Person.waitingToSitTime++;

    } else if (Person.state == SITTING) {

        Person.sittingTime++;

        if (Person.sittingTime == MAX_SITTING_TIME)
            Person.state = WAITING_TO_LEAVE;

    } else if (Person.state == WAITING_TO_LEAVE) {
       
        if (exit available)
            Person.leave();
        else
            Person.waitingToLeaveTime++

    } else if (Person.state == LEAVING) {

        Person.leavingTime++;

    }
}

Of course, you should take some things into consideration: If a person, on frame #0, is waiting to sit, and a seat is available, and he sits down; then on the beginning of frame #1, before the think function is called, do you want his sitting time to be 0 or 1? What about his 'waiting to sit' time? These are important things to consider, but the solutions are trivial: just move some ifs/elses around. The good thing is, you don't have to worry about synchronization.

It may be easier to have one intelligent object for the beginning. Things might get complicated if you call the think functions of the queues first, which may update a person's states or times, and then call the think functions of the persons, not knowing if the states or times were already altered by the queues' think functions, etc, etc...
It's easier for the person to add himself to a queue or seat himself on a seat in his own think function rather than having queues and seats that can think and would do these things for the persons themselves.

I hope I am not complicating things, this is really a very easy approach once you get used to it. (And it can be used to simulate any real situation.)
0

Featured Post

Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

  Included as part of the C++ Standard Template Library (STL) is a collection of generic containers. Each of these containers serves a different purpose and has different pros and cons. It is often difficult to decide which container to use and …
Basic understanding on "OO- Object Orientation" is needed for designing a logical solution to solve a problem. Basic OOAD is a prerequisite for a coder to ensure that they follow the basic design of OO. This would help developers to understand the b…
The goal of the tutorial is to teach the user how to use functions in C++. The video will cover how to define functions, how to call functions and how to create functions prototypes. Microsoft Visual C++ 2010 Express will be used as a text editor an…
The goal of the video will be to teach the user the concept of local variables and scope. An example of a locally defined variable will be given as well as an explanation of what scope is in C++. The local variable and concept of scope will be relat…
Suggested Courses
Course of the Month8 days, 5 hours left to enroll

765 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question