-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmain_stab.py
More file actions
152 lines (129 loc) · 4.88 KB
/
Copy pathmain_stab.py
File metadata and controls
152 lines (129 loc) · 4.88 KB
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
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
# -*- coding: utf-8 -*-
"""
Created on Fri Nov 7 17:59:25 2025
@author: dile
"""
import time
import numpy as np
from modsgen import distros
from modsgen import algostab as stab
try:
import cupy as cp
def to_numpy(x):
"""Converts cupy array to numpy, or leaves it."""
return cp.asnumpy(x) if isinstance(x, cp.ndarray) else x
except ImportError:
import numpy as cp
def to_numpy(x):
"""Arrays are already NumPy, so just return them."""
return x
# --- Main Execution ---
start_time = time.time()
# --- DEFINE YOUR PARAMETERS HERE ---
fname = 'synth'
distro = 'exp' # 'exp', 'bpar', 'hyperexp', or 'erlk'
initl = 500
perc = 0.1
s = 1024
# -----------------------------------
input_file_name = f'{fname}_{s}_{distro}'
print(f"Starting simulation for '{distro}' from file: {input_file_name}")
# 1. --- LOAD AND CONFIGURE ---
if distro == 'exp':
# Load data
parser_func = distros.exp_parser
params_dict_cp, classes = distros.load_params(input_file_name, parser_func)
params_dict_np = {key: to_numpy(val) for key, val in params_dict_cp.items()}
requests = params_dict_np.pop('sizes')
probs = params_dict_np.pop('probs')
# Configure Numba params
print("Configuring for Exponential...")
sampler = stab.sample_exp
mu_vals = params_dict_np['mus']
sigma_params_list = [(mu,) for mu in mu_vals]
taus = 1.0 / mu_vals # Mean = 1 / rate
elif distro == 'bpar':
# Load data
parser_func = distros.bpar_parser
params_dict_cp, classes = distros.load_params(input_file_name, parser_func)
params_dict_np = {key: to_numpy(val) for key, val in params_dict_cp.items()}
requests = params_dict_np.pop('sizes')
probs = params_dict_np.pop('probs')
# Configure Numba params
print("Configuring for B-Pareto...")
sampler = stab.sample_bpar
xmins = params_dict_np['xmins']
xmaxs = params_dict_np['xmaxs']
shapes = params_dict_np['shapes']
sigma_params_list = list(zip(xmins, xmaxs, shapes))
# Calculate B-Pareto means
taus = np.zeros_like(shapes)
for i in range(len(shapes)):
k, m, a = xmins[i], xmaxs[i], shapes[i]
if a == 1:
if m == k: taus[i] = k
else: taus[i] = (np.log(m) - np.log(k)) / (k**-1 - m**-1)
else:
num = a * (k**(1-a) - m**(1-a))
den = (1-a) * (k**-a - m**-a)
if den == 0: taus[i] = k
else: taus[i] = num / den
elif distro == 'hyperexp':
# Load data
parser_func = distros.hyperexp_parser
params_dict_cp, classes = distros.load_params(input_file_name, parser_func)
params_dict_np = {key: to_numpy(val) for key, val in params_dict_cp.items()}
requests = params_dict_np.pop('sizes')
probs = params_dict_np.pop('probs')
# Configure Numba params
print("Configuring for Hyperexponential (2-phase)...")
sampler = stab.sample_hyperexp
r1 = params_dict_np['rates_ph1']
r2 = params_dict_np['rates_ph2']
p1 = params_dict_np['pphases']
sigma_params_list = list(zip(r1, r2, p1))
taus = p1 * (1.0 / r1) + (1.0 - p1) * (1.0 / r2) # Mean
elif distro == 'erlk':
# Load data
parser_func = distros.erlk_parser
params_dict_cp, classes = distros.load_params(input_file_name, parser_func)
params_dict_np = {key: to_numpy(val) for key, val in params_dict_cp.items()}
requests = params_dict_np.pop('sizes')
probs = params_dict_np.pop('probs')
# Configure Numba params
print("Configuring for Erlang-k...")
sampler = stab.sample_erlk
rates = params_dict_np['rates']
ks = params_dict_np['ks']
sigma_params_list = list(zip(rates, ks))
taus = 1.0 / rates # Mean = 1 / rate
else:
raise NotImplementedError(f"Distro '{distro}' not implemented yet")
# --- Check Taus ---
if np.isinf(taus).any():
print("ERROR: Mean (tau) is infinite for at least one class. Stopping.")
exit()
# 2. --- RUN GENERALIZED SIMULATION ---
print("Running generalized Numba simulation...")
lmax, ltop, u = stab.lmax_general(
s=s,
classes=classes,
sampler=sampler, # The @njit sampler function
sigma_params_list=sigma_params_list, # The list of param tuples
taus=taus, # The calculated mean service times
requests=requests,
probs=probs,
perc=perc,
initl=initl
)
end_time = time.time()
# 3. --- PRINT RESULTS ---
print("\n___________________________________________")
print(f"Ideal arrival rate: {ltop:.6f}")
print(f"Maximum arrival rate: {lmax:.6f}")
print(f"Maximum utilization: {u:.6f}")
loads = np.array([0.75])
arrivals = [round(v, 4) for v in loads * lmax]
print("lambdas=({})".format(" ".join(map(str, arrivals))))
print(f"Execution time: {end_time - start_time:.4f} seconds")
print("___________________________________________\n")