process is added to resource user list before request event yields

Issue #62 resolved
Wim Vancroonenburg
created an issue

Hi,

I'm trying to model a simple hospital admission simulation. There is one shared, capacitated resource, namely the number of hospital beds. Patients stay in the hospital for a lognormally distributed amount of time.

The patient process is modelled as this (ward.beds is the shared resource):

def patient_process(env, id,sid, mean_los, sd_los,ward):

    mu, sigma = to_log_norm_param(mean_los, sd_los)
    t = random.lognormvariate(mu=mu, sigma=sigma)

    print("Posting admission request for Patient",id,". Current occupied beds:",ward.beds.count, "Current queueing:",len(ward.beds.queue))
    with ward.beds.request() as req:
        print("Current occupied beds:",ward.beds.count,"Current queueing:",len(ward.beds.queue))
        yield req
        print("Patient", id, "admitted to ward at", env.now, "! Current occupied beds:",ward.beds.count, "Current queueing:",len(ward.beds.queue))
        yield env.timeout(t)

    print("Patient", id, "departure at", env.now, "! Current occupied beds:",ward.beds.count, "Current queueing:",len(ward.beds.queue))

The patient processes are generated with a governing arrival process (exponential interarrival times):

def arrival_process(env, rate, ward):

    id = 0
    while True:
        sid = random.randint(0,2)
        print("Patient", id, "arrival at", env.now, "!")
        env.process(patient_process(env, id,sid, 3, 2, ward))
        id += 1

        t = random.expovariate(rate)
        yield env.timeout(t)

This gives some output like this:

Patient 0 arrival at 0 !
Posting admission request for Patient 0 . Current occupied beds: 0 Current queueing: 0
Current occupied beds: 1 Current queueing: 1
Patient 0 admitted to ward at 0 ! Current occupied beds: 1 Current queueing: 0
Patient 1 arrival at 0.7830303032937973 !
Posting admission request for Patient 1 . Current occupied beds: 1 Current queueing: 0
Current occupied beds: 2 Current queueing: 1
Patient 1 admitted to ward at 0.7830303032937973 ! Current occupied beds: 2 Current queueing: 0
Patient 2 arrival at 1.156097138791643 !
Posting admission request for Patient 2 . Current occupied beds: 2 Current queueing: 0
Current occupied beds: 3 Current queueing: 1
Patient 2 admitted to ward at 1.156097138791643 ! Current occupied beds: 3 Current queueing: 0
Patient 3 arrival at 1.9772868371090317 !
Posting admission request for Patient 3 . Current occupied beds: 3 Current queueing: 0
Current occupied beds: 4 Current queueing: 1
Patient 3 admitted to ward at 1.9772868371090317 ! Current occupied beds: 4 Current queueing: 0
Patient 4 arrival at 2.228350633360595 !
Posting admission request for Patient 4 . Current occupied beds: 4 Current queueing: 0
Current occupied beds: 4 Current queueing: 1
Patient 1 departure at 2.6403677982190583 ! Current occupied beds: 3 Current queueing: 1
Patient 4 admitted to ward at 2.6403677982190583 ! Current occupied beds: 4 Current queueing: 0
Patient 5 arrival at 2.7896250831361558 !
Posting admission request for Patient 5 . Current occupied beds: 4 Current queueing: 0
Current occupied beds: 4 Current queueing: 1

As you can see, between "with req as ward.beds.request()" and "yield req" the patient already occupies the bed (i.e. the process is appended to the users list) , if it is available.
This seems odd to me, or am I doing something which is not intended?

Comments (8)

  1. Ontje Lünsdorf

    Hi Wim,

    I think you discovered an inconsistency. It is not a critical bug, because it is only visible for requests that are immediately triggered. If you print req.triggered on the offending line, you should see that only triggered events look wrong. The inconsistency vanishes, once the request gets processed (e.g. after yield).

    I will try to fix this issue, but it may take some time, because I need to write additional tests. Anyhow, I hope this information helps you to find a workaround at least for the time being.

  2. Wim Vancroonenburg reporter

    Hi luensdorf.

    Thx for the update. I was just exploring Simpy a bit and that's how I noticed this behavior. So it's not a big deal for me, but it does seem like an inconsistency that may be better to resolve. However, I have no idea on what the impact of that would be.

  3. Ontje Lünsdorf

    Enforce an invariant for resource queues. Triggered requests must be removed
    immediately from the queue. Otherwise, immediately successful request will
    remain in users and queue until they become processed. This is inconsistent.
    Fixes #62.

    → <<cset 243b5543cf15>>

  4. Log in to comment