1function [G,R,U]=QBD_NI(A0,A1,A2,varargin)
2%QBD_NI Newton Iteration
for Quasi-Birth-Death Markov Chains [Ramaswami,
7% G=QBD_NI(A0,A1,A2) computes the minimal nonnegative solution to the
8% matrix equation G = A0 + A1 G + A2 G^2, where A,B and C are square
9% nonnegative matrices, with (A0+A1+A2) irreducible and stochastic
11% [G,R]=QBD_NI(A0,A1,A2) also provides the minimal nonnegative solution
12% to the matrix equation R = A2 + R A1 + R^2 A0
14% [G,R,U]=QBD_NI(A0,A1,A2) also provides the minimal nonnegative solution
15% to the matrix equation U = A1 + A2 (I-U)^(-1) A0
17% CONTINUOUS TIME CASE:
19% G=QBD_NI(A0,A1,A2) computes the minimal nonnegative solution to the
20% matrix equation 0 = A0 + A1 G + A2 G^2, where A,B and C are square
21% nonnegative matrices, with (A0+A1+A2) having row sums equal to zero
23% [G,R]=QBD_NI(A0,A1,A2) also provides the minimal nonnegative solution
24% to the matrix equation 0 = A2 + R A1 + R^2 A0
26% [G,R,U]=QBD_NI(A0,A1,A2) also provides the minimal nonnegative solution
27% to the matrix equation U = A1 + A2 (-U)^(-1) A0
31% MaxNumIt: Maximum number of iterations (default: 50)
32% Verbose: The residual error
is printed at each step when set to 1,
34% Mode:
'Sylvest' solves a Sylvester matrix equation at each step
35% using an Hessenberg algorithm
36%
'Estimat' estimates the solution of the Sylvester equation
37%
'DirectSum' solves the Sylvester matrix equation at each
38% step by rewriting it as a (large) system of linear equations
51OptionValues{1}=[
'Sylvest ';
56for i=1:size(OptionNames,1)
57 options.(deblank(OptionNames(i,:)))=[];
61%options.ProgressBar=0;
62options.Mode='Sylvest';
66% Convert to discrete time problem, if needed
69if (sum(diag(A1)<0)) % continues time
78QBD_ParsePara(A0,A1,A2);
80% Parse Optional Parameters
81options=ParseOptPara(options,OptionNames,OptionTypes,OptionValues,varargin);
83% check whether G
is known explicitly
84[G,R,U]=QBD_EG(A0,A1,A2,options.Verbose,nargout);
95while (check > 10^(-12) && numit < options.MaxNumIt)
98 Yk=A2*(eye(m)-A1)^(-1);
100 if (strcmp(options.Mode,'Estimat'))
101 FRk=(A2+R*(A1-eye(m)+R*A0)); % FRk = (A2+RA1+R^2A0)-R
102 Zk=FRk*(eye(m)-A1)^(-1);
103 Yk=FRk+Zk*A1+(R*Zk+Zk*R)*A0;
105 D=-(A2+R*(A1-eye(m)+R*A0)); % D = R-(A2+RA1+R^2A0)
107 % Solve R*Yk*A0+Yk*C=D
108 if (strcmp(options.Mode,'Sylvest'))
109 Yk=QBD_NI_Sylvest(A0',R',C',D')';
111 Yk=(kron(A0',R)+kron(C',eye(m)))^(-1)*reshape(D,m^2,1);
118 if (options.Verbose==1)
119 fprintf('Check after %d iterations: %d\n',numit,check);
124if (numit == options.MaxNumIt && check > 10^(-12))
125 warning('Maximum Number of Iterations %d reached',numit);
129G=(eye(m)-(A1+R*A0))^(-1)*A0;
131if (options.Verbose==1)
132 res_norm=norm(G-A0-(A1+A2*G)*G,inf);
133 fprintf('Final Residual Error for G: %d\n',res_norm);
138 if (options.Verbose==1)
139 res_norm=norm(R-A2-R*(A1+R*A0),inf);
140 fprintf('Final Residual Error for R: %d\n',res_norm);
147 if (options.Verbose==1)
148 res_norm=norm(U-A1-A2*(eye(m)-U)^(-1)*A0,inf);
149 fprintf('Final Residual Error for U: %d\n',res_norm);