LINE Solver (C++)
Templated C++ port of the LINE queueing solver
Toggle main menu visibility
Loading...
Searching...
No Matches
fj_char_max_discrete.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_FJ_CHAR_MAX_DISCRETE_H
6
#define LINE_API_FJ_CHAR_MAX_DISCRETE_H
7
8
/**
9
* @file
10
* @ingroup api_fj
11
* Characteristic maximum of a lattice random variable.
12
*
13
* Templated port of matlab/src/api/fj/fj_char_max_discrete.m.
14
*
15
* With m_K the smallest integer at which P(X > m_K) <= 1/K,
16
*
17
* M_K = m_K + K sum_{k >= m_K} P(X > k),
18
*
19
* which upper bounds the expected maximum of K i.i.d. copies at O(1) instead of
20
* the alternating binomial sum. Two lattice laws close the tail sum:
21
*
22
* geometric, P(X = k) = (1-p) p^k:
23
* m_K = ceil(-ln K / ln p), M_K = m_K + K p^(m_K+1)/(1-p),
24
* exact E[Y_K] = sum_k C(K,k) (-1)^(k+1) p^k/(1-p^k);
25
* Poisson:
26
* M_K = m_K (1 - K P(X > m_K)) + K theta P(X > m_K - 1).
27
*/
28
29
#include <cmath>
30
#include <cstddef>
31
#include <vector>
32
33
#include "
line/api/fj/fj_types.h
"
34
#include "
line/num/number.h
"
35
#include "
line/util/error.h
"
36
37
namespace
line
{
38
namespace
fj
{
39
40
/** The lattice laws for which the characteristic maximum is closed. */
41
enum class
FJDiscreteDist
{
Geometric
,
Poisson
};
42
43
/** [MK, mK, exact] of fj_char_max_discrete. */
44
template
<
class
T>
45
struct
FJCharMaxDiscreteResult
{
46
T
MK
;
47
unsigned
mK
;
48
T
exact
;
49
};
50
51
/**
52
* @brief Characteristic maximum of a lattice random variable.
53
*
54
* @param K number of i.i.d. copies, K >= 1
55
* @param dist the lattice law
56
* @param par p in (0,1) for the geometric, theta > 0 for the Poisson
57
* @return characteristic maximum, its threshold, and the exact maximum
58
*/
59
template
<
class
T>
60
FJCharMaxDiscreteResult<T>
fj_char_max_discrete
(
unsigned
K,
FJDiscreteDist
dist,
const
T& par) {
61
detail::require_positive_K(K,
"fj_char_max_discrete"
);
62
const
T zero =
num_traits<T>::from_int
(0), one =
num_traits<T>::from_int
(1);
63
FJCharMaxDiscreteResult<T>
out;
64
65
if
(dist ==
FJDiscreteDist::Geometric
) {
66
const
T p = par;
67
if
(!(p > zero) || !(p < one))
68
throw
InputError
(
"fj_char_max_discrete: the geometric parameter must lie in (0,1)"
);
69
// Smallest integer k with p^k <= 1/K
70
const
double
mkd = -std::log(
static_cast<
double
>
(K)) /
71
std::log(
num_traits<T>::to_double
(p));
72
long
mk =
static_cast<
long
>
(std::ceil(mkd - 1e-12));
73
if
(mk < 0) mk = 0;
74
out.
mK
=
static_cast<
unsigned
>
(mk);
75
T pw = one;
76
for
(
unsigned
e = 0; e <= out.
mK
; ++e) pw *= p;
77
out.
MK
=
num_traits<T>::from_int
(mk) +
num_traits<T>::from_int
(
static_cast<
long
>
(K)) * pw /
78
(one - p);
79
// Exact maximum by inclusion-exclusion on the geometric tail
80
T acc = zero;
81
T pk = one;
82
for
(
unsigned
k = 1; k <= K; ++k) {
83
pk *= p;
84
const
T term = detail::fj_binom<T>(K, k) * pk / (one - pk);
85
if
(k % 2 == 1) acc += term;
else
acc -= term;
86
}
87
out.
exact
= acc;
88
return
out;
89
}
90
91
const
T theta = par;
92
if
(!(theta > zero))
93
throw
InputError
(
"fj_char_max_discrete: the Poisson mean must be positive"
);
94
const
double
th =
num_traits<T>::to_double
(theta);
95
const
std::size_t kmax =
static_cast<
std::size_t
>
(std::ceil(th + 12 * std::sqrt(th) + 40));
96
std::vector<T> pmf(kmax + 1), cdf(kmax + 1), tail(kmax + 1);
97
T term = detail::num_exp<T>(-theta);
98
T acc = zero;
99
for
(std::size_t k = 0; k <= kmax; ++k) {
100
if
(k > 0) term = term * theta /
num_traits<T>::from_int
(
static_cast<
long
>
(k));
101
pmf[k] = term;
102
acc += term;
103
cdf[k] = (acc > one) ? one : acc;
104
tail[k] = one - cdf[k];
105
}
106
std::size_t mk = kmax + 1;
107
const
T thr = one /
num_traits<T>::from_int
(
static_cast<
long
>
(K));
108
for
(std::size_t k = 0; k <= kmax; ++k)
109
if
(tail[k] <= thr) { mk = k;
break
; }
110
if
(mk > kmax)
111
throw
NumericError
(
"fj_char_max_discrete: the Poisson lattice truncation never reached 1/K"
);
112
out.
mK
=
static_cast<
unsigned
>
(mk);
113
const
T tail_prev = (mk == 0) ? one : tail[mk - 1];
114
out.
MK
=
num_traits<T>::from_int
(
static_cast<
long
>
(mk)) *
115
(one -
num_traits<T>::from_int
(
static_cast<
long
>
(K)) * tail[mk]) +
116
num_traits<T>::from_int
(
static_cast<
long
>
(K)) * theta * tail_prev;
117
// Exact maximum as the sum over the lattice of 1 - F(k)^K
118
T ex = zero;
119
for
(std::size_t k = 0; k <= kmax; ++k) {
120
T pw = one;
121
for
(
unsigned
e = 0; e < K; ++e) pw *= cdf[k];
122
ex += one - pw;
123
}
124
out.
exact
= ex;
125
return
out;
126
}
127
128
}
// namespace fj
129
}
// namespace line
130
131
#endif
// LINE_API_FJ_CHAR_MAX_DISCRETE_H
line::InputError::InputError
InputError(const std::string &what)
Definition
error.h:39
line::NumericError::NumericError
NumericError(const std::string &what)
Definition
error.h:45
error.h
The exception types the port throws.
fj_types.h
Shared return types and arithmetic helpers for the templated fork-join port.
line::fj
Definition
fj_amva.h:34
line::fj::fj_char_max_discrete
FJCharMaxDiscreteResult< T > fj_char_max_discrete(unsigned K, FJDiscreteDist dist, const T &par)
Characteristic maximum of a lattice random variable.
Definition
fj_char_max_discrete.h:60
line::fj::FJDiscreteDist
FJDiscreteDist
The lattice laws for which the characteristic maximum is closed.
Definition
fj_char_max_discrete.h:41
line::fj::FJDiscreteDist::Geometric
@ Geometric
Definition
fj_char_max_discrete.h:41
line::fj::FJDiscreteDist::Poisson
@ Poisson
Definition
fj_char_max_discrete.h:41
line
Definition
aoi_dist2ph.h:52
number.h
Number-type abstraction for the templated API port.
line::fj::FJCharMaxDiscreteResult
[MK, mK, exact] of fj_char_max_discrete.
Definition
fj_char_max_discrete.h:45
line::fj::FJCharMaxDiscreteResult::MK
T MK
Definition
fj_char_max_discrete.h:46
line::fj::FJCharMaxDiscreteResult::mK
unsigned mK
Definition
fj_char_max_discrete.h:47
line::fj::FJCharMaxDiscreteResult::exact
T exact
Definition
fj_char_max_discrete.h:48
line::num_traits
Definition
number.h:111
include
line
api
fj
fj_char_max_discrete.h
Generated by
1.18.0