-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathmain.py
109 lines (90 loc) · 3.23 KB
/
main.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
# -*- coding: utf-8 -*-
"""
Discrete-event simulator that can be used as a basis for most types of
discrete-event simulations. This version is an example that simulates a G/G/c
queuing system. The code is based on the lecture notes of the Stochastic
Simulation course from the Eindhoven University of Technology.
"""
from scipy import stats
from distribution import Distribution
from event import Event
from fes import FES
from simulation_results import SimResults
class Simulation:
'''
Simulates a GGc queuing system
'''
def __init__(self, arr_dist: Distribution, serv_dist: Distribution, nr_servers: int) -> None:
'''
Parameters
----------
arr_dist : object
Object of the Distribution class that contains that can be used to
derive the distribution of the arrivals.
serv_dist : object
Object of the Distribution class that contains that can be used to
derive the distribution of the serving time.
nr_servers : int
The number of servers that can process the arrivals.
Returns
-------
None.
'''
self.arr_dist = arr_dist
self.serv_dist = serv_dist
self.nr_servers = nr_servers
def simulate(self, sim_time: int) -> SimResults:
'''
Parameters
----------
sim_time : int
total run time of the simulation.
Returns
-------
SimResults
object from the SimResults() class that can be used to
extract meaningful results from the simulation
'''
queue = 0
time = 0
results = SimResults()
fes = FES()
first_event = Event(Event.ARRIVAL, self.arr_dist.rvs())
fes.add(first_event)
while time < sim_time:
event = fes.next()
time = event.time
results.register_queue_length(time, queue)
if event.type == Event.ARRIVAL:
queue += 1
if queue <= self.nr_servers:
dep = Event(Event.DEPARTURE, time + self.serv_dist.rvs())
fes.add(dep)
arrival = Event(Event.ARRIVAL, time + self.arr_dist.rvs())
fes.add(arrival)
elif event.type == Event.DEPARTURE:
queue -= 1
if queue >= self.nr_servers:
dep = Event(Event.DEPARTURE, time + self.serv_dist.rvs())
fes.add(dep)
return results
def main(sim_time: int) -> SimResults:
'''
Parameters
----------
sim_time : int
total run time of the simulation.
Returns
-------
object
results object from the SimResults() class that can be used to
extract meaningful results from the simulation such as queue lenght.
'''
arr_dist = Distribution(stats.expon(scale = 1/5.0)) # 5 arrivals p/h
serv_dist = Distribution(stats.expon(scale = 1/1.0)) # process 1 arrival p/h per server
sim = Simulation(arr_dist, serv_dist, nr_servers = 3)
results = sim.simulate(sim_time = sim_time)
return results
if __name__ == "__main__":
SIM_TIME = 100
res = main(sim_time = SIM_TIME)