1function pi=QBD_pi(B0,B1,R,varargin)
2%QBD_pi Stationary vector of a Quasi-Birth-Death Markov Chains [Neuts]
6% pi=QBD_pi(B0,B1,R) computes the stationary vector of a Quasi-Birth-Death
7% Markov chain with a transition matrix of the form
15% the input matrix R
is the minimal nonnegative solution to the matrix
16% equation R = A2 + R A1 + R^2 A0
18% CONTINUOUS TIME CASE:
20% pi=QBD_pi(B0,B1,R) computes the stationary vector of a Quasi-Birth-Death
21% Markov chain with a rate matrix of the form
29% the input matrix R
is the minimal nonnegative solution to the matrix
30% equation 0 = A2 + R A1 + R^2 A0
34% MaxNumComp: Maximum number of components (
default: 500)
35% Verbose: The accumulated probability mass
is printed at every
36% n steps when set to n (default:0)
37% Boundary: Allows solving the QBD with a more general boundary
41%
P (or Q) = 0 A0 A1 A2 0 ...
45% the parameter value contains the matrix [B2; A1+R*A0].
46% The matrices B0 and B2 need not to be square.
48% RAPComp: set to 1 if the QBD has RAP components
64for i=1:size(OptionNames,1)
65 options.(deblank(OptionNames(i,:)))=[];
70options.MaxNumComp=500;
74% Parse Optional Parameters
75options=ParseOptPara(options,OptionNames,OptionTypes,OptionValues,varargin);
79% Convert to discrete time problem, if needed
80if (sum(diag(B1)<0) || options.RAPComp) % continuous time
82 if (~isempty(options.Boundary))
84 lamb=max(lamb,max(-diag(options.Boundary(mb+1:end,:))));
85 options.Boundary=options.Boundary/lamb;
86 options.Boundary(mb+1:end,:)=options.Boundary(mb+1:end,:)+eye(m);
95if( max(temp<-100*eps) )
96 error('MATLAB:QBD_pi:InvalidRInput',...
97 'The spectral radius of R
is not below 1: QBD
is not pos. recurrent');
100if (isempty(options.Boundary))
101 pi=stat(B1+R*B0); % compute pi_0
102 pi=pi/(pi*temp*ones(m,1)); % normalize pi_0
105 while (sumpi < 1-10^(-10) && numit < 1+options.MaxNumComp)
106 pi(numit+1,1:m)=pi(numit,:)*R; % compute pi_(numit+1)
108 sumpi=sumpi+sum(pi(numit,:));
109 if (~mod(numit,options.Verbose))
110 fprintf('Accumulated mass after %d iterations: %d\n',numit,sumpi);
114 pi=reshape(pi',1,[]);
117 pi0=stat([[B1; B0] options.Boundary]); % compute pi_0 and pi_1
118 pi0=pi0/(pi0(1:mb)*ones(mb,1)+pi0(mb+1:end)*temp*ones(m,1)); % normalize
121 sumpi=sum(pi0)+sum(pi);
123 while (sumpi < 1-10^(-10) && numit < options.MaxNumComp)
124 pi(numit+1,1:m)=pi(numit,:)*R; % compute pi_(numit+1)
126 sumpi=sumpi+sum(pi(numit,:));
127 if (~mod(numit,options.Verbose))
128 fprintf('Accumulated mass after %d iterations: %d\n',numit,sumpi);
132 pi=[pi0 reshape(pi',1,[])];
136if (numit == 1+options.MaxNumComp)
137 warning('Maximum Number of Components %d reached',numit-1);