SignRestrictedSVAR.identify#

SignRestrictedSVAR.identify()[source]#

Draw rotations and keep those satisfying every declared sign.

Return type:

SignRestrictedSVARResult

Returns:

The accepted set.

Raises:
  • SpecificationError – If no rotation is accepted within the attempt budget – the signs are jointly unsatisfiable at this reduced form, or nearly so.

  • NumericalError – If the innovation covariance is not positive definite.

Example

The same seed gives the same set; on a system whose responses alternate in sign, requiring both variables to rise at leads zero and one is nearly unsatisfiable and the budget runs out:

>>> import numpy as np
>>> from cultivars.multivariate.reduced_form.vector_autoregression import VAR
>>> rng = np.random.default_rng(0)
>>> B = np.array([[1.0, 0.5], [0.3, 1.0]])
>>> y = np.zeros((402, 2))
>>> for t in range(1, 402):
...     y[t] = 0.4 * y[t - 1] + B @ rng.standard_normal(2)
>>> res = VAR(y, order=1, names=("gdp", "infl")).fit()
>>> signs = {"demand": {"gdp": "+", "infl": "+"}}
>>> first = SignRestrictedSVAR(res, signs, draws=30, seed=1).identify()
>>> again = SignRestrictedSVAR(res, signs, draws=30, seed=1).identify()
>>> bool(np.allclose(first.impacts, again.impacts)), first.attempts == again.attempts
(True, True)
>>> flip = np.zeros((402, 2))
>>> for t in range(1, 402):
...     flip[t] = -0.9 * flip[t - 1] + B @ rng.standard_normal(2)
>>> alternating = VAR(flip, order=1, names=("gdp", "infl")).fit()
>>> SignRestrictedSVAR(
...     alternating, signs, horizons=(0, 1), draws=10, max_attempts=200
... ).identify()
Traceback (most recent call last):
cultivars.exceptions.SpecificationError: no rotation satisfied the declared signs ...