1% [masses, iniF, KF, cloF, iniB, KB, cloB] = SecondOrderLevelDependentFluidSolve (Q, R, S, T, boundaryL, boundaryU, Qt, prec)
3% * Q: cell of generators in
the different layers/regimes
4% * R: cell of diagonal matrices of fluid rates in
the different layers/regimes
5% * S: cell of diagonal matrices of fluid variances in
the different layers/regimes
6% * T: vector of thresholds
7% * boundaryL/U: vector defining
the lower and
the upper boundary behavior
8% one item
for each state of
the background process
9% =0: reflective boundary (
default)
10% =1: absorbing boundary
12% The performance measures (pdf, cdf, etc.) can be computed by
the
13% LevelDependentFluidStationaryDistr function.
15function [masses, iniF, KF, cloF, iniB, KB, cloB] = SecondOrderLevelDependentFluidSolve (Q, R, S, T, boundaryL, boundaryU, Qt, prec)
20 if ~exist(
'prec',
'var')
23 if ~exist('boundaryL','var')
24 boundaryL = zeros(K,N);
26 if ~exist('boundaryU','var')
27 boundaryU = boundaryL;
29 if ~exist('Qt','var') || isempty(Qt)
64 ix0 = ix(abs(diag(R{k}))<=prec & diag(S{k})<=prec);
65 ixn0 = setdiff(ix,ix0);
70 Qnn = Q{k}(ixn0,ixn0);
72 Qv = Qnn + Qn0*inv(-Q00)*Q0n;
78 % partition
the state space according to zero, positive and negative fluid rates
80 ixp = ix(diag(Rv)>prec & diag(Sv)<=prec);
81 ixn = ix(diag(Rv)<-prec & diag(Sv)<=prec);
82 ixs = ix(diag(Sv)>prec);
89 % obtain
"c" constant to transform matrix equations to QBD like matrix
91 c1 = max(-diag(Qv(ixp,ixp))./diag(Rv(ixp,ixp)));
92 discr = (diag(Rv(ixs,ixs)).^2 - 2*diag(2*Sv(ixs,ixs)).*diag(Qv(ixs,ixs)));
93 c2 = max((discr>0).*((-diag(Rv(ixs,ixs))+sqrt(discr))./diag(2*Sv(ixs,ixs))));
97 NbF(k) = length(ixbF);
99 Bm = blkdiag(c*Sv(ixbF,ixbF),-Rv(ixn,ixn));
100 Lm = [-Rv(ixbF,ixbF)-2*c*Sv(ixbF,ixbF),zeros(NbF(k),Nn(k));Qv(ixn,ixbF)/c,Qv(ixn,ixn)/c+Rv(ixn,ixn)];
101 Fm = [Qv(ixbF,ixbF)/c+c*Sv(ixbF,ixbF)+Rv(ixbF,ixbF),Qv(ixbF,ixn)/c;zeros(Nn(k),NbF(k)+Nn(k))];
103 % Solve QBD
for matrix R
104 [~, QBDR] = QBD_CR(Bm, Lm, Fm);
106 % extract K and Psi from
the solution
107 KF{k} = (QBDR(1:NbF(k),1:NbF(k)) - eye(NbF(k))) * c;
108 PsiF = QBDR(1:NbF(k),NbF(k)+1:end);
110 % closing matrix of
the stationary density of
the fluid level
112 clovF = zeros(NbF(k),NbF(k)+Nn(k));
113 clovF(:,ixbF) = eye(NbF(k));
116 cloF{k} = zeros(NbF(k),N);
117 cloF{k}(:,ixn0) = clovF;
118 cloF{k}(:,ix0) = clovF*Qn0*inv(-Q00);
120 % BACKWARD parameters
122 % obtain
"c" constant to transform matrix equations to QBD like matrix
123 % quadratic equations
124 c1 = max(-diag(Qv(ixn,ixn))./diag(-Rv(ixn,ixn)));
125 discr = (diag(Rv(ixs,ixs)).^2 - 2*diag(2*Sv(ixs,ixs)).*diag(Qv(ixs,ixs)));
126 c2 = max((discr>0).*((diag(Rv(ixs,ixs))+sqrt(discr))./diag(2*Sv(ixs,ixs))));
130 NbB(k) = length(ixbB);
132 Bm = blkdiag(c*Sv(ixbB,ixbB),Rv(ixp,ixp));
133 Lm = [Rv(ixbB,ixbB)-2*c*Sv(ixbB,ixbB),zeros(NbB(k),Np(k));Qv(ixp,ixbB)/c,Qv(ixp,ixp)/c-Rv(ixp,ixp)];
134 Fm = [Qv(ixbB,ixbB)/c+c*Sv(ixbB,ixbB)-Rv(ixbB,ixbB),Qv(ixbB,ixp)/c;zeros(Np(k),NbB(k)+Np(k))];
136 % Solve QBD
for matrix R
137 [~, QBDR] = QBD_CR(Bm, Lm, Fm);
139 % extract K and Psi from
the solution
140 KB{k} = (QBDR(1:NbB(k),1:NbB(k)) - eye(NbB(k))) * c;
141 PsiB = QBDR(1:NbB(k),NbB(k)+1:end);
143 % closing matrix of
the stationary density of
the fluid level
144 clovB = zeros(NbB(k),NbB(k)+Np(k));
145 clovB(:,ixbB) = eye(NbB(k));
148 cloB{k} = zeros(NbB(k),N);
149 cloB{k}(:,ixn0) = clovB;
150 cloB{k}(:,ix0) = clovB*Qn0*inv(-Q00);
156 vixsn{k} = ixn0(diag(Sv)>prec & diag(Rv)<0);
157 vixsp{k} = ixn0(diag(Sv)>prec & diag(Rv)>=0);
158 vixs0{k} = ixn0(diag(Sv)>prec & diag(Rv)==0);
164 % Construct and solve linear set of equations
for the unknows (probability
165 % masses and density parameters iniF and iniB
for all regimes)
166 % ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
167 Neqns = (K+1)*N + sum(Np) + sum(Nn) + 2*sum(Ns);
170 M = sparse(Neqns,Neqns);
176 pos = [pos, N, NbF(k), NbB(k)];
181 % equalities
for flux conservation
183 M(pp(i):pp(i)+N-1,k*N+1:(k+1)*N) = -Qt{k+1};
185 M(pp(i-2):pp(i-2)+NbF(k)-1,k*N+1:(k+1)*N) = expm(KF{k}*(T(k+1)-T(k)))*(-cloF{k}*R{k} + KF{k}*cloF{k}*S{k});
186 M(pp(i-1):pp(i-1)+NbB(k)-1,k*N+1:(k+1)*N) = -cloB{k}*R{k} - KB{k}*cloB{k}*S{k};
189 M(pp(i+1):pp(i+1)+NbF(k+1)-1,k*N+1:(k+1)*N) = cloF{k+1}*R{k+1}-KF{k+1}*cloF{k+1}*S{k+1};
190 M(pp(i+2):pp(i+2)+NbB(k+1)-1,k*N+1:(k+1)*N) = expm(KB{k+1}*(T(k+2)-T(k+1)))*(cloB{k+1}*R{k+1} + KB{k+1}*cloB{k+1}*S{k+1});
201 % mass
is zero in positive and in reflective states
202 ixr0 = intersect(ix(boundaryL==0), vixs{1});
204 ms0 = zeros(N,Np(1)+Nr0);
205 ms0([vixp{1},ixr0],:) = eye(Np(1)+Nr0);
206 M(pp(i):pp(i)+N-1,col:col+Np(1)+Nr0-1) = ms0;
207 col = col + Np(1)+Nr0;
208 % density
is zero in absorbing states
209 ixa0 = intersect(ix(boundaryL==1), vixs{1});
212 pdfB = expm(KB{1}*T(2))*cloB{1};
213 M(pp(i+1):pp(i+1)+NbF(k+1)-1,col:col+Na0-1) = pdfF(:,ixa0);
214 M(pp(i+2):pp(i+2)+NbB(k+1)-1,col:col+Na0-1) = pdfB(:,ixa0);
217 % mass
is zero in negative and in reflective states
218 ixrB = intersect(ix(boundaryU==0), vixs{K});
220 ms0 = zeros(N,Nn(K)+NrB);
221 ms0([vixn{K},ixrB],:) = eye(Nn(K)+NrB);
222 M(pp(i):pp(i)+N-1,col:col+Nn(K)+NrB-1) = ms0;
223 col = col + Nn(K)+NrB;
224 % density
is zero in absorbing states
225 ixaB = intersect(ix(boundaryU==1), vixs{K});
227 pdfF = expm(KF{K}*(T(K+1)-T(K)))*cloF{K};
229 M(pp(i-2):pp(i-2)+NbF(k)-1,col:col+NaB-1) = pdfF(:,ixaB);
230 M(pp(i-1):pp(i-1)+NbB(k)-1,col:col+NaB-1) = pdfB(:,ixaB);
233 % there
is no mass except S+(k) U S-(k+1)
234 st0 = setdiff(ix, union(intersect(vixp{k},vixn{k+1}),
union(vix0{k},vix0{k+1})));
237 ms0(st0,:) = eye(N0);
238 M(pp(i):pp(i)+N-1,col:col+N0-1) = ms0;
240 % equations
for the second-order states
241 sts = setdiff(
union(vixs{k},vixs{k+1}),
union(vixn{k+1},vixp{k}));
243 BelowF = expm(KF{k}*(T(k+1)-T(k)))*-cloF{k}*sqrt(S{k});
244 BelowB = -cloB{k}*sqrt(S{k});
245 AboveF = cloF{k+1}*sqrt(S{k+1});
246 AboveB = expm(KB{k+1}*(T(k+2)-T(k+1)))*cloB{k+1}*sqrt(S{k+1});
247 M(pp(i-2):pp(i-2)+NbF(k)-1,col:col+Nss-1) = BelowF(:,sts);
248 M(pp(i-1):pp(i-1)+NbB(k)-1,col:col+Nss-1) = BelowB(:,sts);
249 M(pp(i+1):pp(i+1)+NbF(k+1)-1,col:col+Nss-1) = AboveF(:,sts);
250 M(pp(i+2):pp(i+2)+NbB(k+1)-1,col:col+Nss-1) = AboveB(:,sts);
256 %
this function computes
the integral of a matrix exponential from 0 to
257 % L
if it has a 0 eigenvalue hence can not be inverted
258 function KAi = integExp(KA,L)
262 KAi = inv(-(KA-r*l)) *(eye(size(KA,1))-expm((KA-r*l)*L)) + r*l*(L+exp(-L)-1);
265 %
this function receives two matrices and calculates
the integrals of
266 %
the matrix exponentials
if exactly one of them has a 0 eigenvalue
267 function [KAi,KBi] = integExp2(KA,KB,L)
268 if min(abs(eig(KA))) > min(abs(eig(KB)))
269 KAi = inv(-KA)*(eye(size(KA,1))-expm(KA*L));
270 KBi = integExp(KB, L);
272 KAi = integExp(KA, L);
273 KBi = inv(-KB)*(eye(size(KB,1))-expm(KB*L));
277 % normalizing condition
281 [sumKF, sumKB] = integExp2(KF{k}, KB{k}, T(k+1)-T(k));
282 h = [h; sum(sumKF*cloF{k},2); sum(sumKB*cloB{k},2); ones(N,1)];
283 Mi{k} = [sum(sumKF*cloF{k},2); sum(sumKB*cloB{k},2)];
286 % solve linear system
288 b = [1,zeros(1,length(h)-1)]/M;
297 iniF{k} = b(pp(i):pp(i)+NbF(k)-1);
298 iniB{k} = b(pp(i+1):pp(i+1)+NbB(k)-1);
299 masses{k+1} = b(pp(i+2):pp(i+2)+N-1);