LINE Solver (C++)
Templated C++ port of the LINE queueing solver
Toggle main menu visibility
Loading...
Searching...
No Matches
aph_fit_moments.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_MAM_APH_FIT_MOMENTS_H
6
#define LINE_API_MAM_APH_FIT_MOMENTS_H
7
8
/**
9
* @file
10
* @ingroup api_mam
11
* Acyclic phase-type fitters from the first two moments.
12
*
13
* Port of BUTools' `APHFrom2Moments` and of MATLAB `APH.fitMeanAndSCV`. Both
14
* lived in solver_mna.h until a second caller appeared: the closed
15
* setup/delay-off branch of solver_mam_basic fits its delay-off with
16
* `APH.fitMeanAndSCV`, exactly as the reference does, and solver_mna.h already
17
* includes solver_mam_basic.h, so leaving them there would have been a cycle.
18
*
19
* These are NOT the canonical Coxian of `coxian_phase_subgen`
20
* (qbd_setupdelayoff.h). The two agree in the first two moments but not in
21
* shape: the Coxian is entered at phase 1, this APH is entered at phase 1 with
22
* probability p and at the LAST phase otherwise. Anything reading more than the
23
* first two moments -- an LST, for instance -- sees the difference, so a caller
24
* must use whichever one the reference names for that call site.
25
*/
26
27
#include <algorithm>
28
#include <cmath>
29
#include <string>
30
#include <vector>
31
32
#include "
line/api/mam/map_moment.h
"
33
#include "
line/lang/lang_types.h
"
34
#include "
line/num/number.h
"
35
#include "
line/util/error.h
"
36
#include "
line/util/matrix.h
"
37
38
namespace
line
{
39
namespace
mam
{
40
41
/**
42
* Port of BUTools' `APHFrom2Moments`.
43
*
44
* Absorption is possible ONLY from the last phase: the first N-1 rows of the
45
* generator have a zero row sum by construction, so D1 is zero everywhere
46
* except its last row. That is the shape, not an artifact of the fit.
47
*/
48
template
<
class
T>
49
Map<T>
aph_from_2moments
(
const
T& e1,
const
T& e2) {
50
const
T zero =
num_traits<T>::from_int
(0), one =
num_traits<T>::from_int
(1);
51
const
T cv2 = T(T(e2 / T(e1 * e1)) - one);
52
const
double
cv2d =
num_traits<T>::to_double
(cv2);
53
if
(!(cv2d > 0.0))
54
throw
NumericError
(
55
"APHFrom2Moments: the moment pair implies a non-positive squared coefficient of "
56
"variation ("
+ std::to_string(cv2d) +
57
"), for which the reference's order ceil(1/cv2) is not a positive integer"
);
58
const
T lambda = T(one / e1);
59
const
long
N = std::max(
static_cast<
long
>
(std::ceil(1.0 / cv2d)), 2L);
60
const
std::size_t n =
static_cast<
std::size_t
>
(N);
61
const
T Nt =
num_traits<T>::from_int
(N);
62
const
T p = T(one / T(cv2 + one + T(T(cv2 - one) /
num_traits<T>::from_int
(N - 1))));
63
64
Matrix<T>
A(n, n, zero);
65
const
T d = T(lambda * p * Nt);
66
for
(std::size_t i = 0; i < n; ++i) A(i, i) = T(-d);
67
for
(std::size_t i = 0; i + 1 < n; ++i) A(i, i + 1) = d;
68
A(n - 1, n - 1) = T(-T(lambda * Nt));
69
70
std::vector<T> alpha(n, zero);
71
alpha[0] = p;
72
alpha[n - 1] = T(one - p);
73
74
Map<T>
m;
75
m.
D0
= A;
76
m.
D1
=
Matrix<T>
(n, n, zero);
77
for
(std::size_t i = 0; i < n; ++i) {
78
T ex = zero;
79
for
(std::size_t j = 0; j < n; ++j) ex += A(i, j);
80
for
(std::size_t j = 0; j < n; ++j) m.
D1
(i, j) = T(-ex * alpha[j]);
81
}
82
return
m;
83
}
84
85
/** Port of `APH.fitMeanAndSCV`, the entry point the analyzers fit arrivals with. */
86
template
<
class
T>
87
Map<T>
aph_fit_mean_scv
(
const
T& mean,
const
T& scv) {
88
const
T zero =
num_traits<T>::from_int
(0), one =
num_traits<T>::from_int
(1);
89
if
(
num_traits<T>::to_double
(mean) <=
lang::GlobalConstants::FineTol
) {
90
// A sub-tolerance mean is answered by an exponential, and a
91
// non-positive one by the Zero-mean surrogate the reference names.
92
const
T m = (mean > zero) ? mean :
num_traits<T>::from_double
(
lang::GlobalConstants::Zero
);
93
return
map_exponential
(T(one / m));
94
}
95
if
(scv == one)
return
map_exponential
(T(one / mean));
96
return
aph_from_2moments
(mean, T(T(one + scv) * mean * mean));
97
}
98
99
}
// namespace mam
100
}
// namespace line
101
102
#endif
// LINE_API_MAM_APH_FIT_MOMENTS_H
line::Matrix
Definition
matrix.h:56
line::Matrix::Matrix
Matrix()
Definition
matrix.h:58
line::NumericError::NumericError
NumericError(const std::string &what)
Definition
error.h:45
error.h
The exception types the port throws.
lang_types.h
Enumerations and the minimal distribution descriptor shared by the model layer of the C++ port.
map_moment.h
Markovian arrival process descriptors: stationary vectors, rate, moments, autocorrelation and the ind...
matrix.h
Dense matrix and non-owning view.
line::mam
Definition
amap2_adjust_gamma.h:78
line::mam::aph_fit_mean_scv
Map< T > aph_fit_mean_scv(const T &mean, const T &scv)
Port of APH.fitMeanAndSCV, the entry point the analyzers fit arrivals with.
Definition
aph_fit_moments.h:87
line::mam::aph_from_2moments
Map< T > aph_from_2moments(const T &e1, const T &e2)
Port of BUTools' APHFrom2Moments.
Definition
aph_fit_moments.h:49
line::mam::map_exponential
Map< T > map_exponential(const T &lambda)
Two-phase MAP constructor for a Poisson process of rate lambda.
Definition
map_moment.h:213
line
Definition
aoi_dist2ph.h:52
number.h
Number-type abstraction for the templated API port.
line::lang::GlobalConstants::FineTol
static constexpr double FineTol
Definition
lang_types.h:668
line::lang::GlobalConstants::Zero
static constexpr double Zero
Definition
lang_types.h:670
line::mam::Map
A MAP as the pair of matrices (D0, D1).
Definition
map_moment.h:53
line::mam::Map::D1
Matrix< T > D1
Definition
map_moment.h:55
line::mam::Map::D0
Matrix< T > D0
Definition
map_moment.h:54
line::num_traits
Definition
number.h:111
include
line
api
mam
aph_fit_moments.h
Generated by
1.18.0