Authors: |
|
---|---|
Date: | 2003-November-12 |
SimPy version: | 1.5 |
Web-site: | http://simpy.sourceforge.net/ |
Python-Version: | 2.2, 2.3, 2.4 |
There have been no changes to the SimPy 1.4 API, so existing code under SimPy 1.5 works as before.
Two major synchronization/scheduling facilities have been added to SimPy:
- events and signalling, with yield waitevent and yield queueevent
- process waiting for arbitrary conditions, with yield waituntil
This document briefly outlines the commands available in SimPy. It refers to SimPy version 1.4 or later. The facilities described require Python 2.2 or later. (When using Python 2.2, the following import statement must be used at the head of SimPy scripts: from __future__ import generators)
A SimPy model is made up of Processes, Resources and Monitors and operations on them.
Basic structure of a SimPy simulation:
Processes inherit from class Process, imported from SimPy.Simulation.
By the process itself:
By other processes:
self.interrupt(victim) interrupts another process. The interrupt is just a signal. After this statement, the interrupting process immediately continues its current method.
The victim must be active to be interrupted (that is executing a yield hold,self,t) otherwise the interruption has no effect.
The introduction of interrupts changes the semantics of yield hold. After before=now(); yield hold,self,T, we have the post-condition now()== before+T OR (self.interrupted() AND now()< before+T). The program must allow for this, i.e., for interrupted, incomplete activities.
When interrupted, the victim prematurely and immediately returns from its yield hold. It can sense if it has been interrupted by calling:
self.interrupted() which returns True if it has been interrupted. If so:
The interruption is reset at the victims next call to a yield hold,. Alternatively it can be reset by calling
self.interruptReset()
The modeller may define Resources. These inherit from class Resource which is imported at the start of the program: from SimPy.Simulation import Resource
A Resource, r, is established using the command:
A Resource, r, has the following attributes:
A unit of resource, r, can be requested and later released by a process using the following yield commands:
If a Resource, r is defined with priority queueing (that is qType==PriorityQ) a request can be made for a unit by:
If a Resource, r, is defined with priority queueing (that is qType=PriorityQ) and also preemption (that is preemptable=1) a request can be made for a unit by:
If there are several lower priority processes, that with the lowest priority is suspended, put at the front of the waitQ and the higher priority, preempting process gets its resource unit and is put into the activeQ. The preempted process is the next one to get a resource unit (unless another preemption occurs). The time for which the preempted process had the resource unit is taken into account when the process gets into the activeQ again. Thus, the total hold time is always the same, regardless of whether or not a process gets preempted.
SimPy uses the standard random variate routines in the Python random module. To use them, import the random module:
A good range of distributions is available. For example:
SimPy 1.5 introduces two advanced process scheduling, event signalling and a general "wait until" construct. They complement the existing scheduling facilities, such as yield hold, and can make the implementation of many simulation models easier. Because they are higher level constructs,they can lead to much clearer and shorter scripts.
Events in SimPy are implemented by class SimEvent. This name was chosen because the term 'event' is already being used in Python for e.g. Tkinter events or in Python's standard library module signal -- Set handlers for asynchronous events.
An instance of a SimEvent is generated by something like myEvent=SimEvent("MyEvent"). Associated with a SimEvent are
- a boolean occurred to show whether an event has happened (has been signalled)
- a list waits, implementing a set of processes waiting for the event
- a list queues, implementing a FIFO queue of processes queueing for the event
- an attribute signalparam to receive an (optional) payload from the signal method
Processes can wait for events by issuing:
yield waitevent,self,<events part>
<events part> can be:
- an event variable, e.g. myEvent)
- a tuple of events, e.g. (myEvent,myOtherEvent,TimeOut), or
- a list of events, e.g. [myEvent,myOtherEvent,TimeOut]
Processes can queue for events by issuing:
yield queueevent,self,<events part> (with <events part> as defined above)
If one of the events in <events part> has already happened, the process contines. The occurred flag of the event(s) is toggled to False.
If none of the events in the <events part> has happened, the process is passivated after joining the FIFO queue of processes queuing for all the events.
The ocurrence of an event is signalled by:
<event>.signal(<payload parameter>)
The <payload parameter> is optional. It can be of any Python type.
When issued, signal causes the occurred flag of the event to be toggled to True, if waiting set and and queue are empty. Otherwise, all processes in the event's waits list are reactivated at the current time, as well as the first process in its queues FIFO queue.
A process can wait for an arbitrary condition by issuing:
yield waituntil,self,<cond>
where <cond> is a reference to a function without parameters which returns the state of the condition to be waited for as a boolean value.
The "wait until" construct is the most powerful synchronization construct. It effectively generalizes all other SimPy synchronization constructs, i.e., it could replace all of them (but at a runtime cost).
Monitors are part of the SimPy package.
To define a new Monitor object:
object, set to '' if it is missing.
Methods:
Simple data summaries:
Deprecated methods:
The following methods are retained for backwards compatibility but are not recommended. They mey be removed in future releases of SimPy:
This provides an easy way to graph the results of simulation runs. See the SimPlot Manual.
These messages are returned by simulate(), as in message=simulate(until=123).
Upon a normal end of a simulation, simulate() returns the message:
The following messages, returned by simulate(), are produced at a premature termination of the simulation but allow continuation of the program.
These messages are generated when SimPy-related fatal exceptions occur. They end the SimPy program. Fatal SimPy error messages are output to sysout.
We will be grateful for any corrections or suggestions for improvements to the document.
Version: | $Revision: 1.4 $ :Date: $Date: 2004-12-03 13:12:19+01 $ gav |
---|---|
Python-Version: | 2.2, 2.3 |
Created: | 2002-December-10 |