Short explanation of a simulation program with a future event list
Note: This program simulates a user and a server. It uses a simulation framework that could easily be used for modeling other systems.
The program contains the following classes (blue means that the class is part of the simulation framework that can be reused for simulating other systems; green means that some modifications may be required, black means that the class is application-specific):
- Main
- SimSystem - an instance of this represents the simulation system. The simulation loop gets the next event from the future event list and passes it on the the instance of active object identified by the target attribute of the event. This active object must handle the event.
- EventHandler - abstract Class representing all simulated active object classes in the simulated system
- Server - one of the active object classes simulated
- User - one of the active object classes simulated
- Event - instances of this class are stored in the event list (of type FutureEventList), sorted by increasing values of the time attribute. The action attribute indicates what type of event is represented by the instance. Other attributes are defined depending on the semantics of the actions that are performed by the active objects when the handle the reception of an event.
- EventNode - a node in the future event list
- FutureEventList
- TimePeriodExp - used to get a random time duration according to some given distribution
- CalculateAverage - defines objects that can accumulate the average of some series of numbers
- EventQueue - waiting queue of the Server
Explanations
The SimSystem object created by the main program contains the description of the system to be simulated and also contains the list of future events, called future, and the simulation loop which is executed within the constructor of the SimSystem class. In the future event list, the events are ordered according to the scheduled execution time (simulated time).
A scheduled event, in addition to its time indicated when it should be executed, contains the following information: (a) the action, which means what kind of action should be performed when this event is executed; (b) the target, which is a reference of an object that should perform the execution of this action, and some other data. In this example, the other data is used to store an identifier, which represents the number of user request to which this event belongs.
The target object is of type EventHandler which is an abstract class. In this example, there are two types of EventHandlers; they are of type Server or User. Each EventHandler supports a method, called handleEvent(Event e) which performs the execution of the event. These methods are called by the simulation loop in the SimSystem. The SimSystem, itself, is also an EventHandler; it looks after the events that are generated for taking measurement snapshots (in this example, the queue length of the server and the question whether the server is free or busy are recorded in two arrays which are processed when the simulation terminates.
Note that the Server process, when processing the end of a service time (action SERVE_END) may generate a new event with the same identifier to be handled by another Server, if such a server was connected during the contruction process (in this example, the reference to another server is null).
The following is an overview of the actions performed when the different events are processed:
- Action USER_REQ processed by the User object: forward the event with action NEW_REQ to be handled by the associated Server instance. Then create a new event (with increased identifier) to be scheduled (in the future) at a time randomly chosen.
- Action NEW_REQ processed by the Server object: if the server is free, schedule this event with the action SERVE_END for a time randomly chosen corresponding to the service time distribution; the server becomes occupied. Otherwise, put the event into the waiting queue of the server.
- Action SERVE_END processed by the Server object: (the server should be occupied) Set the server free and forward the event to another EventHandler (if this is desired). If some event is waiting in the queue, process this event by scheduling a corresponding event with a SERVE_END action (note that the time of the event in the queue is the time when this event was entered into the queue, and not the current time of the simulation process (which is always the time of the event which was provided with the call of the handleEvent method.
Written March 2010, revised March 2011, March 2016