LINE Solver
MATLAB API documentation
Loading...
Searching...
No Matches
MarkedMAP.m
1classdef MarkedMAP < MarkovModulated
2 % Markov Modulated Arrival Process
3 %
4 % Copyright (c) 2012-2026, Imperial College London
5 % All rights reserved.
6
7 methods
8 %Constructor
9 function self = MarkedMAP(D,K)
10 % SELF = MarkedMAP(D,K)
11 %
12 % LINE uses the M3A representation format
13 % D={D0, D1, D11, D12, D13, ..., D1K}
14 % K is the number of marking types
15
16 self@MarkovModulated('MarkedMAP',K+2);
17
18 if K == length(D)-1
19 setParam(self, 1, 'D0', D{1});
20 setParam(self, 2, 'D1', cellsum({D{2:end}}));
21 for k=1:K
22 setParam(self, 2+k, sprintf('D1%d',k), D{1+k});
23 end
24 elseif K == length(D)-2
25 setParam(self, 1, 'D0', D{1});
26 setParam(self, 2, 'D1', D{2});
27 for k=1:K
28 setParam(self, 2+k, sprintf('D1%d',k), D{2+k});
29 end
30 else
31 line_error(mfilename,'Inconsistency between the number of classes and the number of supplied D matrices.')
32 end
33 % Copy all K+2 params {D0, D1, D11, ..., D1K} into the process
34 % cell (M3A layout); copying only K entries would truncate the
35 % per-mark matrices and break D(1,k)/getNumberOfTypes.
36 MarkedMAP = cell(1,K+2);
37 for k=1:K+2
38 MarkedMAP{k} = self.getParam(k).paramValue;
39 end
40 self.process = MarkedMAP;
41 end
42
43 function Di = D(self, i, j, wantSparse)
44 % Di = D(i)
45 if nargin == 1
46 Di = self.getProcess;
47 return
48 end
49 if nargin<4
50 wantSparse = false;
51 end
52 if nargin<3
53 if i<=1
54 j = 0;
55 else
56 line_error(mfilename,'Invalid D matrix indexes');
57 end
58 end
59
60 % Return representation matrix, e.g., D0=MAP.D(0)
61 if wantSparse
62 if nargin<2
63 Di=self.getProcess;
64 else
65 Di=self.getProcess{1+i+j};
66 end
67 else
68 if nargin<2
69 Di=self.getProcess;
70 for i=1:length(Di)
71 Di(i)=full(Di(i));
72 end
73 else
74 Di=full(self.getProcess{1+i+j});
75 end
76 end
77 end
78
79 function meant = evalMeanT(self, t)
80 % MEANT = EVALMEANT(SELF,T)
81
82 meant = self.toMAP.evalMeanT(t);
83 end
84
85 function vart = evalVarT(self, t)
86 % VART = EVALVART(SELF,T)
87
88 % Evaluate the variance-time curve at timescale t
89 vart = self.toMAP.evalVarT(t);
90 end
91
92 function acf = evalACFT(self, lags, timescale)
93 % ACF = EVALACFT(self, lags)
94 %
95 % Evaluate the autocorrelation in counts at timescale t
96
97 acf = self.toMAP.evalACFT(lags, timescale);
98 end
99
100 % inter-arrival time properties
101 function mean = getMean(self)
102 % MEAN = GETMEAN()
103
104 mean = self.toMAP.getMean;
105 end
106
107 function scv = getSCV(self)
108 % SCV = GETSCV()
109
110 scv = self.toMAP.getSCV;
111 end
112
113 % inter-arrival time properties for each marking type
114 function mean = getMarkedMeans(self)
115 % MEAN = GETMARKEDMEANS()
116
117 mean = 1 ./ mmap_lambda(self.D);
118 end
119
120 function acf = getACF(self, lags)
121 % ACF = GETACF(self, lags)
122
123 acf = self.toMAP.getACF(lags);
124 end
125
126 function map = toMAP(self)
127 map = MAP(self.D(0), self.D(1));
128 end
129
130 function maps = toMAPs(self, types)
131 if nargin<2
132 types = 1:self.getNumberOfTypes;
133 end
134 maps = {};
135 for k=types
136 Df = self.D(0);
137 Df = Df + (self.D(1) - self.D(1,k));
138 maps{end+1} = MAP(Df, self.D(1,k));
139 end
140 end
141
142 function [gamma2, gamma] = getACFDecay(self)
143 % [gamma2, gamma] = GETACFDECAY(self)
144 %
145 % gamma2: asymptotic decay rate of acf
146 % gamma: interpolated decay rate of acf
147
148 [gamma2, gamma] = self.toMAP.getACFDecay();
149 end
150
151 function id = getIDC(self, t) % index of dispersion for counts
152 % ID = GETIDC() % INDEX OF DISPERSION
153 if nargin < 2
154 id = self.toMAP.getIDC;
155 else
156 id = self.toMAP.getIDC(t);
157 end
158 end
159
160 function id = getMarkedIDC(self, t) % asymptotic index of dispersion for counts for each type
161 % ID = GETMARKEDIDC() % ASYMPTOTIC INDEX OF DISPERSION
162 if nargin < 2
163 id = mmap_count_idc(self.getProcess, GlobalConstants.Immediate);
164 else
165 id = mmap_count_idc(self.getProcess, t);
166 end
167 end
168
169 function lam = getRate(self)
170 % LAMBDA = GETRATE()
171
172 lam = self.toMAP.getRate;
173 end
174
175 function n = getNumberOfPhases(self)
176 % N = GETNUMBEROFMAPASES()
177 D0 = self.getParam(1).paramValue;
178 n = length(D0);
179 end
180
181 function mu = getMu(self)
182 % MU = GETMU()
183 % Aggregate departure rate from each state
184 mu = sum(self.D(1),2); % sum D1 rows / diag -D0
185 end
186
187 function phi = getPhi(self)
188 % MAPI = GETMAPI()
189 % Return the exit vector of the underlying MAP
190 phi = sum(self.D(1),2) ./ diag(-self.D(0)); % sum D1 rows / diag -D0
191 end
192
193 function K = getNumberOfTypes(self)
194 % K = GETNUMBEROFTYPES()
195 % Number of marking types
196
197 K = length(self.D)-2;
198 end
199
200 function MMAPr = toTimeReversed(self)
201 MMAPr = MarkedMAP(mmap_timereverse(self.D), self.getNumberOfTypes);
202 end
203
204 function [X,C] = sample(self, n)
205 % [X,C] = SAMPLE(N)
206 if nargin<2 %~exist('n','var'),
207 n = 1;
208 end
209 MarkedMAP = self.getProcess;
210 if mmap_isfeasible(MarkedMAP)
211 [X,C] = mmap_sample(MarkedMAP,n);
212 else
213 line_error(mfilename,'This process is infeasible (negative rates).');
214 end
215 end
216
217 end
218
219 methods (Static)
220
221 function mmap = fit(trace, markings, order)
222 % M3PP = FIT(TRACE, ORDER)
223 T = m3afit_init(trace,markings);
224 mmap = m3afit_auto(T,'NumStates',order);
225 end
226
227
228 function mmap = rand(order, nclasses)
229 % MarkedMAP = RAND(ORDER,NCLASSES)
230 %
231 % Generate random MarkedMAP using uniform random numbers
232 if nargin < 1
233 order = 2;
234 end
235 mmap = MarkedMAP(mmap_rand(order,nclasses),nclasses);
236 end
237 end
238end
Definition Station.m:287
Definition Station.m:245