LINE Solver (C++)
Templated C++ port of the LINE queueing solver
Loading...
Searching...
No Matches
qsys_engset.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2012-2026, QORE Lab, Imperial College London
3 * All rights reserved.
4 */
5#ifndef LINE_API_QSYS_QSYS_ENGSET_H
6#define LINE_API_QSYS_QSYS_ENGSET_H
7
8/**
9 * @file
10 * @ingroup api_qsys
11 * Exact analysis of the Engset loss system M/G/c/c/K: K sources, each idle for
12 * an Exp(alpha) time, c servers and no waiting room.
13 *
14 * Port of matlab/src/api/qsys/qsys_engset.m. The number of busy servers has
15 * the truncated binomial law p_n ~ C(K, n) beta^n, n = 0..c, beta = alpha/mu,
16 * which is insensitive to the service law. Time congestion is p_c; call
17 * congestion (what an arriving request sees) is the time congestion of the
18 * same system with K-1 sources.
19 *
20 * ARITHMETIC: double (gammaln, log-space normalization), as the reference.
21 */
22
23#include <algorithm>
24#include <cmath>
25#include <string>
26#include <vector>
27
29#include "line/util/error.h"
30
31namespace line {
32namespace qsys {
33
34namespace engsetdetail {
35/** The truncated binomial occupancy law, normalized in log space. */
36inline std::vector<double> engset_dist(double beta, unsigned c, unsigned K) {
38 std::vector<double> logp(c + 1);
39 for (unsigned n = 0; n <= c; ++n)
40 logp[n] = gammaln(K + 1.0) - gammaln(n + 1.0) - gammaln(static_cast<double>(K) - n + 1.0) + n * std::log(beta);
41 double mx = logp[0];
42 for (double v : logp) mx = std::max(mx, v);
43 std::vector<double> p(c + 1);
44 double s = 0.0;
45 for (unsigned n = 0; n <= c; ++n) s += (p[n] = std::exp(logp[n] - mx));
46 for (double& v : p) v /= s;
47 return p;
48}
49} // namespace engsetdetail
50
51/**
52 * @brief Exact Engset M/G/c/c/K loss system.
53 *
54 * @param alpha request rate of one idle source
55 * @param mu service rate of one server
56 * @param c number of servers
57 * @param K number of sources, K >= c
58 */
59inline QsysRes qsys_engset(double alpha, double mu, unsigned c, unsigned K) {
60 if (!(alpha > 0.0)) throw Error("qsys_engset: alpha must be a positive real scalar");
61 if (!(mu > 0.0)) throw Error("qsys_engset: mu must be a positive real scalar");
62 if (c < 1) throw Error("qsys_engset: c must be a positive integer");
63 if (K < c) throw Error("qsys_engset: K must be an integer >= c");
64 const double beta = alpha / mu;
65 const std::vector<double> p = engsetdetail::engset_dist(beta, c, K);
66 double callCong = 0.0;
67 if (K > 1) {
68 const std::vector<double> pK1 = engsetdetail::engset_dist(beta, std::min(c, K - 1), K - 1);
69 if (c <= K - 1) callCong = pK1.back();
70 }
71 double EN = 0.0, EN2 = 0.0;
72 for (unsigned n = 0; n <= c; ++n) {
73 EN += n * p[n];
74 EN2 += static_cast<double>(n) * n * p[n];
75 }
76 QsysRes r;
77 r.set("timeCongestion", p.back());
78 r.set("callCongestion", callCong);
79 r.set("offeredRate", alpha * (K - EN));
80 r.set("throughput", mu * EN);
81 r.set("meanBusyServers", EN);
82 r.set("varBusyServers", EN2 - EN * EN);
83 r.set("utilization", EN / c);
84 r.set("meanSojournTime", 1.0 / mu);
85 r.set("queueLengthDist", p);
86 r.analyzer = "exact:Engset M/G/" + std::to_string(c) + "/" + std::to_string(c) + "/" + std::to_string(K);
87 return r;
88}
89
90} // namespace qsys
91} // namespace line
92
93#endif // LINE_API_QSYS_QSYS_ENGSET_H
Error(const std::string &what)
Definition error.h:75
The exception types the port throws.
std::vector< double > engset_dist(double beta, unsigned c, unsigned K)
The truncated binomial occupancy law, normalized in log space.
Definition qsys_engset.h:36
double gammaln(double x)
MATLAB's gammaln.
Definition qsys_res.h:111
QsysResT< double > QsysRes
Definition qsys_res.h:96
QsysRes qsys_engset(double alpha, double mu, unsigned c, unsigned K)
Exact Engset M/G/c/c/K loss system.
Definition qsys_engset.h:59
Conservation laws of a layered queueing network, enumerated from its structure.
Definition aoi_dist2ph.h:52
The res struct the exact queueing-system functions return, and the numeric helpers those functions sh...
std::string analyzer
Definition qsys_res.h:59
void set(const std::string &name, const T &v)
Sets (or overwrites) a scalar field.
Definition qsys_res.h:62