1.3. Zero-th order approximation: steady state and balanced-growth path
The most flexible way to approach the solving of the steady state
and the balanced-growth path is through the writing of a separate
steady-state file. (Setting the steady state inside the model
file via @steady_state_model is also supported – see
Model file language.)
1.3.1. Anatomy of a steady-state file
A steady-state file is a plain MATLAB function (name of your choice). Its signature:
[y, newp, retcode] = my_ssfile(m, y, p, d, id)
Args:
m– model object (not always needed).y–endo_nbr x 1vector of initial steady state (stationary models) orendo_nbr x 2matrix of initial steady state and growth rate (non-stationary models).p– parameter structure.d– definitions.id– locations of the variables to calculate.
Returns:
y– the updated steady-state vector (or vector + growth rate for non-stationary models).newp– structure of updated parameters, if any (a steady state can pin parameters implied by SS conditions; these belong here, not as numerics in the params file).retcode–0if no problems, non-zero otherwise.
Note
The steady-state file is regime-agnostic:
The same file is valid whether the model has many regimes or not.
The user does not need to know which regime is being computed.
It is in sync with the steady-state model.
RISE calls the function twice:
First call with one argument (the model object only). Collects:
the list of variables for which the steady state is solved and the order in which the calculations will be returned;
the list of parameters whose value is computed in the steady state.
Second call with all input arguments. The user returns the steady state and the steady-state-computed parameters.
A complete listing, for a simple non-stationary model:
function [y, newp, retcode] = simple_ssfile(m, y, p, d, id)
retcode = 0;
if nargin == 1
% list of endogenous variables to be calculated and the
% order in which they will appear
y = {'Y','Z','h'};
newp = {}; % list of parameters computed during SS
else
% steady states and new parameter values
newp = struct();
h = [1/3, 0];
Z = [p.zss, p.mu];
Y = [Z(1)*h(1), Z(2)];
ys = [Y; Z; h]; % order matches the list above
if any(isnan(ys(:)))
retcode = 1;
else
y(id, :) = ys;
end
end
end
1.3.2. Incomplete analytical solution
Sometimes the user’s program does not solve the steady state or the balanced-growth path completely. This can occur because the user can only calculate part of the steady state, or because RISE created auxiliary variables (notably the Lagrange multipliers under optimal policy).
While RISE knows how to handle its own auxiliary variables, it falls back to a numerical solve for the remaining variables given the partial steady state the user supplied.
1.3.3. Steady-state loops
Sometimes the user can compute the steady state conditional on the knowledge of a particular variable. For instance, in an optimal-policy problem where only monetary policy is missing, knowing steady-state inflation may pin every other endogenous variable (Lagrange multipliers excluded).
Write a steady-state file that takes the missing variables as given. RISE proposes values for those missing variables in the second argument of the steady-state file. The locations of the missing variables come from:
get(m, 'endo_list')
Set the option sstate_loop to true to inform RISE that
only a subset of variables is unknown.
1.3.4. Facilitators
Several facilitators help the numerical solve and can be combined.
Equation simplification
The user provides both a dynamic equation and a steady-state
companion (the #-companion form, see Model file language):
log(X{t}) = (1-rho)*log(xss) + rho*log(X{t-1}) + sig*E{t} #
X{t} = xss;
log(Z{t}/Z{t-1}) = log(muz) + sigz*EZ{t} #
Z{t} = muz*Z{t-1};
Declaring log and level variables
Besides the economic interpretation, taking log approximations restricts the search domain for log variables to \((0, +\infty)\), which prevents:
division by 0;
log of zero;
log of negative values.
Setting bounds on variables
RISE accepts user-defined bounds on the search space for the steady state and the growth rate of variables under a numerical solve.
1.3.5. Steady states of growing variables in the dynamic equations
On a balanced growth path the steady state of a growing variable is not a
number but a path. When a dynamic equation refers to the steady state of
the lead of a variable, stst(V{+1}) (also steady_state(V{+1})), and
the variable grows, RISE reads it as an anchor that moves with the
trend, not as the value of the path at the date of the expansion. In the
coordinates of the dynamic equations (the log of a log variable) it is
replaced by the reference that @cognitive_discount uses:
\(Z\) are the exogenous stochastic trends RISE finds in the equations (an own equation with only its lags, parameters and shocks and a unit root, e.g.
A = A{-1}*gz*exp(sig*E); or a level whose first difference is such a process), at their realized value;\(X\) carry the other trend directions (a variable with a first-difference variable, e.g. the log price level
p = p{-1} + pi, or a log variable whose steady state is written this way), at their previous value plus one period of trend growth;the exponents \(b\) (parameters
cdtrend_<V>_<carrier>) are the loadings of \(V\) on the trend directions, recomputed after every steady-state solve. A stationary variable has \(b=0\): its anchor is its steady state, as before.
For the log price level with p = p{-1} + pi and a target pis:
stst(p{+1}) + m*(p{+1} - stst(p{+1}))
is p + pis + m*(pi{+1} - pis): the anchor of p{t+1} is
p{t} + pis. The expectation is p{t} + pis when m = 0 and
p{t+1} when m = 1. With a unit-root technology A and a
consumption C that grows like it, stst(C{+1}) is
stst(C{+1})*A{+1}/stst(A{+1}), so a hand-written discounting
stst(C{+1}) + mcd*(C{+1} - stst(C{+1})) keeps the balanced growth path
an equilibrium for every mcd. Before this change the anchor was the
fixed date-0 value and, for mcd < 1, the solution drifted away from the
path without shocks.
Limits:
only leads,
stst(V{+1}), are rewritten.stst(V)and the steady states of lags, of expressions and of exogenous variables stay the steady state at the expansion date;models without any trend carrier (no unit-root exogenous process, no first-difference variable) are parsed exactly as written;
a growing variable that loads on a trend direction no carrier spans keeps the fixed anchor, with the warning
rise:stst:fixedAnchor;the steady-state model and files, the
@epilogueand the planner objective are not touched. In an optimal-policy model the rewrite applies only when the expectations are formed before the first-order conditions (br_b4_opt_policy = true); otherwise the equations stay as written;@cognitive_discountbuilds the same reference for the leads of the variables it tags: a steady state written by hand and one created by the discounting are treated once, alike.
1.3.6. Multiple regimes
The presence of multiple regimes does not add complexity for the steady-state computation. The steady state is computed either:
at the ergodic mean of the parameters (Foerster, Rubio-Ramirez, Waggoner and Zha, 2016); or
with a different vector of parameters per regime (Maih-Waggoner, 2018; Chang et al., 2021).