code: def test_simulation_exog():
      # GH 551
      burn = 250
      from arch.univariate import Normal
  
      rs = np.random.RandomState(3382983)
      normal = Normal(seed=rs)
      x_mod = ARX(None, lags=1, distribution=normal)
      x0 = x_mod.simulate([1, 0.8, 1], nobs=1000 + burn).data
      x1 = x_mod.simulate([2.5, 0.5, 1], nobs=1000 + burn).data
  
      rs = np.random.RandomState(33829831)
      normal = Normal(seed=rs)
      resid_mod = ZeroMean(volatility=GARCH(), distribution=normal)
      resids = resid_mod.simulate(
          [0.1, 0.1, 0.8], nobs=1000 + burn
      ).data
  
      phi1 = 0.7
      phi0 = 3
      y = 10 + resids.copy()
      for i in range(1, y.shape[0]):
          y[i] = (
              phi0 + phi1 * y[i - 1] + 2 * x0[i] - 2 * x1[i] + resids[i]
          )
  
      x0 = x0.iloc[-1000:]
      x1 = x1.iloc[-1000:]
      y = y.iloc[-1000:]
      y.index = x0.index = x1.index = np.arange(1000)
  
      x0_oos = np.empty((1000, 10))
      x1_oos = np.empty((1000, 10))
      for i in range(10):
          if i == 0:
              last = x0
          else:
              last = x0_oos[:, i - 1]
          x0_oos[:, i] = 1 + 0.8 * last
          if i == 0:
              last = x1
          else:
              last = x1_oos[:, i - 1]
          x1_oos[:, i] = 2.5 + 0.5 * last
  
      exog = pd.DataFrame({"x0": x0, "x1": x1})
      mod = arch_model(y, x=exog, mean="ARX", lags=0)
      res = mod.fit(disp="off")
  
      nforecast = 3
  
      # DECOMMENT ONE OF THE FOLLOWING LINES
      exog_fcast = {
          "x0": np.zeros_like(x0_oos[-nforecast:]),
          "x1": np.zeros_like(x1_oos[-nforecast:]),
      }
      forecasts = res.forecast(
          horizon=10,
          x=exog_fcast,
          start=1000 - nforecast,
          method="simulation",
      )
  
      exog_fcast = {
          "x0": np.zeros_like(x0_oos),
          "x1": np.zeros_like(x0_oos),
      }
      forecasts_alt = res.forecast(
          horizon=10,
          x=exog_fcast,
          start=1000 - nforecast,
          method="simulation",
      )
      assert_allclose(forecasts.mean, forecasts_alt.mean)
  
      exog_fcast = {
          "x0": 10 + np.zeros_like(x0_oos[-nforecast:]),
          "x1": 10 + np.zeros_like(x1_oos[-nforecast:]),
      }  # case with shape (nforecast, horizon)
      # exog_fcast = {"x0": x0_oos, "x1": x1_oos} # case with shape (nobs, horizon)
  
      forecasts_10 = res.forecast(
          horizon=10,
          x=exog_fcast,
          start=1000 - nforecast,
          method="simulation",
      )
  
      delta = forecasts_10.mean - forecasts.mean
      expected = (10 * res.params[["x0", "x1"]]).sum() + np.zeros_like(
          delta
      )
      assert_allclose(delta, expected)
  
imports: import datetime
  from itertools import product
  import numpy
  from numpy.random import RandomState
  from numpy.testing import assert_allclose
  import pandas
  from pandas.testing import assert_frame_equal
  import pytest
  from arch.data import sp500
  from arch.tests.univariate.test_variance_forecasting import preserved_state
  from arch.univariate import APARCH, ARX, EGARCH, FIGARCH, GARCH, HARCH, HARX, ConstantMean, ConstantVariance, EWMAVariance, MIDASHyperbolic, RiskMetrics2006, ZeroMean, arch_model
  from arch.univariate.mean import _ar_forecast, _ar_to_impulse
label_desc: Use image node_id 14 for calling a global function with example usage: test_simulation_exog() without return types