尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

VARMA模型可扩展估计:高维时间序列参数估计与正则化实践

VARMA模型可扩展估计:高维时间序列参数估计与正则化实践 1. 先搞清楚 VARMA 模型到底解决什么统计问题如果你处理过时间序列数据尤其是多变量时间序列比如同时分析多个城市的温度、多个股票的价格、多个经济指标的变化那你肯定遇到过 ARIMA 模型。ARIMA 擅长处理单个序列但当序列之间相互影响时就需要它的“升级版”——VARMA 模型。VARMA 的全称是向量自回归移动平均模型它解决的核心问题是如何在一个统一的统计框架下同时刻画多个时间序列变量自身的动态变化规律以及它们彼此之间的相互影响关系。这听起来有点抽象我举个例子。假设你手上有三个时间序列GDP增长率、通货膨胀率和失业率。它们之间显然不是孤立的GDP增长可能影响就业通胀可能影响货币政策进而影响增长。VARMA 模型能做的就是用一个数学方程系统把“今天的 GDP 增长率受昨天 GDP、通胀、失业率多少影响”以及“今天的通胀率又受昨天哪些变量影响”这些复杂关系通过一组参数自回归系数和移动平均系数给量化出来。它的价值在于一旦模型被准确估计出来你就可以用它来做三件事理解变量间的动态关系、预测未来的走势、以及评估某个冲击比如政策变化对整个系统会产生怎样的连锁反应。所以这篇文章不是一篇纯理论推导而是面向实际应用。我会重点拆解“可扩展的估计”这个关键点。在现实中VARMA 模型参数多、估计复杂当变量数量增加时计算量会急剧膨胀甚至变得不可行。因此“可扩展的估计”方法就是为了解决在大规模、高维度时间序列数据下如何高效、稳定地拟合 VARMA 模型的问题。这直接决定了这个强大的工具能否从教科书走进你的实际数据分析项目。2. 理解 VARMA 模型的结构与核心参数在动手估计之前必须对模型本身有清晰的认识。VARMA(p, q) 模型由两部分组成向量自回归 (VAR) 部分和向量移动平均 (VMA) 部分。一个标准的 VARMA(p, q) 模型可以写成如下形式[ \mathbf{y}t \mathbf{c} \sum{i1}^{p} \mathbf{\Phi}i \mathbf{y}{t-i} \mathbf{\epsilon}t \sum{j1}^{q} \mathbf{\Theta}j \mathbf{\epsilon}{t-j} ]这里每个符号都代表一个矩阵或向量(\mathbf{y}_t)一个 (k \times 1) 的向量表示在时间 (t) 观测到的 (k) 个时间序列变量。(\mathbf{c})一个 (k \times 1) 的常数项向量。(\mathbf{\Phi}_i)第 (i) 个 (k \times k) 的自回归系数矩阵。它描述了 (\mathbf{y}_{t-i}) 对当前值 (\mathbf{y}_t) 的影响。(\mathbf{\epsilon}_t)一个 (k \times 1) 的随机扰动项向量通常假设为白噪声均值为0协方差矩阵为 (\mathbf{\Sigma})。(\mathbf{\Theta}_j)第 (j) 个 (k \times k) 的移动平均系数矩阵。它描述了过去的扰动 (\mathbf{\epsilon}_{t-j}) 对当前值 (\mathbf{y}_t) 的影响。(p)自回归阶数。(q)移动平均阶数。为什么参数这么多估计起来困难假设我们有 (k5) 个变量模型阶数 (p2, q1)。那么我们需要估计的参数包括2个 (\mathbf{\Phi}) 矩阵每个是 (5 \times 5 25) 个参数共 50 个。1个 (\mathbf{\Theta}) 矩阵(5 \times 5 25) 个参数。1个常数项向量 (\mathbf{c})5 个参数。1个扰动项协方差矩阵 (\mathbf{\Sigma})由于对称性有 (5 \times (51)/2 15) 个独立参数。加起来总共95 个参数需要从数据中估计。当 (k) 增加到 10 或 20 时参数数量将以平方级增长轻松达到数百甚至上千个。这就是“可扩展性”成为核心挑战的原因传统的极大似然估计 (MLE) 方法在参数过多时会遇到计算复杂度高、数值不稳定、甚至无法收敛的问题。3. 可扩展估计的核心思路与常用方法面对高维参数估计的“维数灾难”研究者们发展出了几种主流的可扩展估计思路。这些方法的核心思想都是通过引入额外的约束或结构来减少需要自由估计的参数数量或者改进优化算法本身。3.1 降维与稀疏性假设这是最直观的思路。既然参数太多那就假设其中很多参数其实是零或接近零即模型具有稀疏性。例如在宏观经济系统中可能并不是所有变量都相互影响很多跨变量的滞后影响很弱。方法包括Lasso 类正则化 (L1正则化)在似然函数中加入参数的绝对值之和作为惩罚项使得优化过程倾向于将不重要的系数压缩至零。对于 VARMA 模型这需要对 (\mathbf{\Phi}) 和 (\mathbf{\Theta}) 矩阵中的每一个元素施加惩罚。组 Lasso 或稀疏组 Lasso考虑到时间序列的滞后结构可以对整个 (\mathbf{\Phi}_i) 矩阵代表第 (i) 阶滞后的所有影响进行分组惩罚或者对描述某个变量受所有其他变量影响的整行/整列系数进行分组惩罚。这比元素级的 Lasso 更有经济意义。贝叶斯方法为参数设置具有稀疏诱导特性的先验分布如 spike-and-slab 先验、马蹄先验等通过后验推断来识别非零参数。实操建议如果你的领域知识告诉你变量间的联系可能是稀疏的比如某些行业股票受大盘影响大但彼此间关联弱优先尝试带 L1 正则化的估计方法。这能同时完成模型估计和变量选择。3.2 利用模型的结构化表示VARMA 模型可以转化为一些等价的、但更易于处理的形式。状态空间模型 (SSM) 表示任何一个 VARMA 模型都可以写成状态空间形式。状态空间模型的好处是可以用卡尔曼滤波进行高效的递归计算特别适合处理长序列数据。估计时可以对状态空间模型中的参数对应 VARMA 参数采用期望最大化 (EM) 算法或基于梯度的优化方法。对于大规模问题可以对状态向量的维度进行压缩或采用并行化的卡尔曼滤波变种。频域方法将时间序列转换到频域在频域上估计谱密度矩阵然后再反推回时域参数。这种方法有时能避免直接处理高维的时域方程组尤其适用于具有特定周期结构的数据。实操建议对于非常长的时间序列比如高频金融数据将其表示为状态空间模型并用卡尔曼滤波处理在计算上往往比直接处理原始的 VARMA 方程更高效、更稳定。很多成熟的统计软件包如 R 的stats包、Python 的statsmodels都内置了状态空间模型的工具。3.3 分步估计与简化模型与其一次性估计所有参数不如采用分而治之的策略。先 VAR 后 MA一种经典的近似方法是先拟合一个高阶的纯 VAR 模型即令 (q0)。因为 VAR 模型的估计是线性的可以通过最小二乘法 (OLS) 高效求解即使维度较高。然后对这个 VAR 模型的残差序列进行分析再估计移动平均 (MA) 部分。虽然这不是精确的 VARMA 估计但在很多情况下提供了一个良好的起点和近似。使用 VAR 近似在很多实际应用中特别是预测任务中一个足够高阶的 VAR 模型可以任意近似一个 VARMA 模型。因此当估计完整的 VARMA 模型过于复杂时直接估计一个高阶 VAR 模型可能配合上述的正则化是一个常用且有效的替代方案。实操建议不要一上来就死磕完整的 VARMA(p,q) 模型。我通常的流程是1) 先尝试拟合一个带正则化的 VAR 模型观察残差是否还有明显的自相关性2) 如果残差很“干净”那么这个 VAR 模型可能已经够用3) 如果残差显示有移动平均结构再考虑引入 MA 部分此时可以基于 VAR 的残差来初始化 MA 参数的估计能大大提高整体优化的成功率。3.4 基于现代优化算法与并行计算当模型必须保留较多参数时计算瓶颈就在于优化算法本身。随机梯度下降 (SGD) 及其变种对于超大规模问题可以使用基于小批量的随机优化算法每次迭代只使用一部分数据计算梯度大大降低单次迭代的计算量。交替方向乘子法 (ADMM)ADMM 非常擅长处理带有可分离结构的、包含正则化项的优化问题。可以将 VARMA 的估计问题分解成几个子问题交替求解每个子问题可能都有解析解或更易求解。并行与分布式计算许多计算步骤可以并行化。例如在计算似然函数或其梯度时对不同时间片段的计算可以独立进行。利用多核 CPU 或 GPU 可以显著加速。实操建议对于普通规模的数据变量数k20样本量T1000使用成熟的统计软件如 MATLAB 的 Econometrics Toolbox, R 的vars或MTS包Python 的statsmodels提供的默认 MLE 或矩估计方法通常就够了。只有当问题规模真正变大时才需要去探索定制化的优化算法或并行实现。此时你可能需要结合TensorFlow、PyTorch利用自动微分和GPU或Julia这类高性能语言来自己实现目标函数和优化流程。4. 从理论到实践一个完整的估计流程与代码示例下面我将以一个模拟的中等规模例子演示一个包含正则化的、相对稳健的 VARMA 模型估计流程。我们使用 Python 的statsmodels库因为它提供了良好的基础。对于更复杂的正则化我们可能需要结合scikit-learn或自定义优化。环境准备Python 3.8主要库numpy,pandas,statsmodels,scikit-learn,matplotlib4.1 步骤一模拟数据生成与初步观察我们先生成一个已知参数的 VARMA(1,1) 数据这样我们可以评估估计效果。import numpy as np import pandas as pd import matplotlib.pyplot as plt from statsmodels.tsa.api import VARMAX from statsmodels.tsa.stattools import adfuller import warnings warnings.filterwarnings(ignore) # 设置随机种子保证可重复性 np.random.seed(12345) # 定义模型参数 k 3 # 3个变量 T 500 # 500个时间点 p_true, q_true 1, 1 # 真实的参数矩阵 # 自回归系数矩阵 Phi (形状: k x k) Phi_true np.array([[0.5, 0.2, -0.1], [0.1, 0.7, 0.0], [0.0, 0.0, 0.4]]) # 移动平均系数矩阵 Theta (形状: k x k) Theta_true np.array([[0.3, 0.0, 0.1], [0.0, 0.2, 0.0], [0.0, 0.0, 0.1]]) # 常数项 c_true np.array([0.1, 0.2, 0.05]) # 扰动项协方差矩阵 Sigma_true np.array([[1.0, 0.5, 0.3], [0.5, 1.0, 0.2], [0.3, 0.2, 1.0]]) # 生成扰动项序列 eps np.random.multivariate_normal(meannp.zeros(k), covSigma_true, sizeT) # 初始化序列 y y np.zeros((T, k)) y[0, :] np.random.multivariate_normal(meannp.zeros(k), covnp.eye(k)*10, size1) # 递归生成 VARMA(1,1) 数据 for t in range(1, T): if t 1: y[t] c_true Phi_true y[t-1] eps[t] else: y[t] c_true Phi_true y[t-1] eps[t] Theta_true eps[t-1] # 转换为 DataFrame df pd.DataFrame(y, columns[y1, y2, y3]) df.index pd.date_range(start2000-01-01, periodsT, freqM) # 可视化 fig, axes plt.subplots(k, 1, figsize(12, 8), sharexTrue) for i, col in enumerate(df.columns): axes[i].plot(df.index, df[col], lw1.5) axes[i].set_title(fSimulated Series: {col}) axes[i].grid(True) plt.tight_layout() plt.show() # 平稳性检验ADF检验 print(平稳性检验 (ADF test p-value):) for col in df.columns: result adfuller(df[col].dropna()) print(f {col}: {result[1]:.4f})关键点生成数据后一定要先做平稳性检验。VARMA 模型通常要求序列是平稳的。如果检验不通过p值大于0.05需要对数据进行差分等处理这实际上是在估计 VARIMA 模型。这是实操中第一个容易忽略的坑。4.2 步骤二模型阶数选择 (p, q)对于真实数据我们不知道真实的 p 和 q。需要基于信息准则来选择。statsmodels的VARMAX不直接提供自动阶数选择我们可以通过循环拟合不同 (p, q) 组合的模型比较 AIC 或 BIC。# 尝试不同的 (p, q) 组合 p_max, q_max 3, 3 results_dict {} aic_matrix np.full((p_max1, q_max1), np.inf) # 包含 (0,0) for p in range(p_max1): for q in range(p_max1): if p 0 and q 0: continue # VARMA(0,0) 无意义 try: print(fFitting VARMA({p},{q})...) model VARMAX(df, order(p, q), trendc) # ‘c’代表包含常数项 result model.fit(dispFalse, maxiter200) # dispFalse 不显示迭代信息 results_dict[(p, q)] result aic_matrix[p, q] result.aic print(f AIC: {result.aic:.2f}) except Exception as e: print(f Failed to fit VARMA({p},{q}): {e}) aic_matrix[p, q] np.inf # 找到 AIC 最小的模型 min_idx np.unravel_index(np.nanargmin(aic_matrix), aic_matrix.shape) p_opt, q_opt min_idx print(f\nOptimal order based on AIC: p{p_opt}, q{q_opt}) print(fMinimum AIC: {aic_matrix[p_opt, q_opt]:.2f}) # 注意对于真实数据BIC可能比AIC更倾向于选择更简洁的模型防止过拟合。为什么先选阶数直接用一个很高的 (p, q) 去拟合不仅计算慢而且容易过拟合模型不稳定。信息准则AIC/BIC在拟合优度和模型复杂度之间做了权衡。我一般会同时看 AIC 和 BIC如果两者选出的阶数差异很大我会更倾向于 BIC 的结果因为它对参数数量的惩罚更重模型更简洁稳健。4.3 步骤三拟合 VARMA 模型并解读结果用选出的最优阶数拟合模型。# 使用最优阶数拟合模型 model_opt VARMAX(df, order(p_opt, q_opt), trendc) result_opt model_opt.fit(dispTrue, maxiter500) # 这次显示迭代信息 print(result_opt.summary()) # 提取关键参数 print(\n 估计的参数与真实值对比 ) print(Estimated Constant (c):) print(result_opt.params[const]) print(True Constant:, c_true) print(\nEstimated AR coefficients (Phi):) # 注意 statsmodels 的参数命名方式可能是 ar.L1.y1, ar.L1.y2... # 我们需要按变量和滞后整理一下。这里简化处理直接查看所有参数。 print(result_opt.params.filter(likear.L1)) # 查看一阶自回归系数 print(True Phi:\n, Phi_true) print(\nEstimated MA coefficients (Theta):) print(result_opt.params.filter(likema.L1)) # 查看一阶移动平均系数 print(True Theta:\n, Theta_true) print(\nEstimated Innovation Covariance Matrix:) print(result_opt.cov_params().iloc[-k:, -k:]) # 协方差矩阵通常在参数列表最后 print(True Sigma:\n, Sigma_true)解读结果摘要summary()输出非常详细。你需要重点关注系数显著性看每个系数对应的P|z|值。通常小于 0.05 或 0.1 认为在统计上显著。不显著的系数意味着该影响可能不存在这为模型简化稀疏性提供了依据。模型诊断摘要底部会提供对模型残差的一系列检验如 Ljung-Box 检验检验残差自相关、Jarque-Bera 检验检验残差正态性。一个拟合良好的模型其残差应该是白噪声。如果检验拒绝白噪声假设说明模型可能阶数不足或形式有误。信息准则确认 AIC/BIC 值与你之前选择时的一致。4.4 步骤四模型诊断与残差分析这是验证模型是否充分捕捉了数据动态的关键一步。# 1. 获取模型残差 residuals result_opt.resid print(Residuals Summary:) print(residuals.describe()) # 2. 残差自相关检验 (Ljung-Box) from statsmodels.stats.diagnostic import acorr_ljungbox print(\nLjung-Box test for residual autocorrelation:) lb_test acorr_ljungbox(residuals, lags[10, 20], return_dfTrue) # 检验10阶和20阶自相关 print(lb_test) # 我们希望 p-value 都大于0.05说明无显著自相关。 # 3. 残差正态性检验 (Jarque-Bera) from scipy import stats print(\nJarque-Bera test for normality:) for col in residuals.columns: jb_stat, jb_pval stats.jarque_bera(residuals[col].dropna()) print(f {col}: statistic{jb_stat:.3f}, p-value{jb_pval:.4f}) # p-value 0.05 不能拒绝正态性假设。 # 4. 绘制残差序列和ACF/PACF图 fig, axes plt.subplots(2, k, figsize(15, 8)) for i, col in enumerate(residuals.columns): # 残差序列图 axes[0, i].plot(residuals.index, residuals[col], lw0.8) axes[0, i].axhline(y0, colorr, linestyle--, lw0.8) axes[0, i].set_title(fResiduals of {col}) axes[0, i].grid(True) # 残差自相关函数 (ACF) 图 from statsmodels.graphics.tsaplots import plot_acf, plot_pacf plot_acf(residuals[col].dropna(), lags20, axaxes[1, i], titlefACF of {col} Residuals) plt.tight_layout() plt.show()诊断标准理想的残差应该看起来像随机波动序列图其 ACF 图没有超出置信区间的显著尖峰说明无自相关。如果残差检验未通过可能需要增加模型阶数 (p, q)或者考虑数据本身存在非线性、结构性变化等问题。4.5 步骤五样本外预测与模型评估模型最终要用于预测。我们将数据分为训练集和测试集。# 划分训练集和测试集 (最后50个点作为测试) train_size T - 50 df_train df.iloc[:train_size] df_test df.iloc[train_size:] # 在训练集上重新拟合最优模型 model_train VARMAX(df_train, order(p_opt, q_opt), trendc) result_train model_train.fit(dispFalse) # 进行样本外预测预测未来50步 forecast_steps 50 forecast_obj result_train.get_forecast(stepsforecast_steps) forecast_mean forecast_obj.predicted_mean # 预测均值 forecast_ci forecast_obj.conf_int() # 预测置信区间 # 将预测结果与真实测试集对比 fig, axes plt.subplots(k, 1, figsize(12, 10), sharexTrue) for i, col in enumerate(df.columns): axes[i].plot(df_train.index, df_train[col], labelTrain, lw1.5) axes[i].plot(df_test.index, df_test[col], labelTest (Actual), lw1.5, colorgreen) axes[i].plot(forecast_mean.index, forecast_mean[col], labelForecast, lw1.5, colorred, linestyle--) axes[i].fill_between(forecast_ci.index, forecast_ci[(col, lower)], forecast_ci[(col, upper)], colorred, alpha0.2) axes[i].set_title(fForecast vs Actual for {col}) axes[i].legend() axes[i].grid(True) plt.tight_layout() plt.show() # 计算预测误差 (例如均方根误差 RMSE) from sklearn.metrics import mean_squared_error rmse_vals {} for col in df.columns: rmse np.sqrt(mean_squared_error(df_test[col], forecast_mean[col])) rmse_vals[col] rmse print(fRMSE for {col}: {rmse:.4f})预测评估RMSE 等指标用于量化预测精度。但更重要的是观察预测图预测值是否抓住了序列的趋势和波动置信区间是否合理覆盖了真实值如果预测在测试集上表现很差可能意味着1) 模型在训练集上过拟合2) 数据生成过程在测试期间发生了结构性变化3) 模型阶数或形式选择不当。5. 当模型规模变大引入正则化与高级技巧上面的例子是“教科书式”的流程。当变量数 (k) 增大到 10、20 甚至更多时statsmodels的默认 MLE 可能会非常慢甚至失败。这时就需要引入第 3 部分讨论的可扩展方法。5.1 使用带惩罚项的估计以 Elastic Net 为例我们可以将 VAR 模型的估计作为 VARMA 的近似或第一步转化为一个带惩罚的回归问题。这里以 Elastic Net结合 L1 和 L2 正则化为例使用scikit-learn。from sklearn.linear_model import ElasticNetCV from sklearn.preprocessing import StandardScaler # 假设我们只想估计一个高阶 VAR 模型作为近似例如 VAR(4) p_large 4 k df.shape[1] T df.shape[0] # 构建滞后变量作为特征 (X)当期值作为目标 (y) # 这是一个多输出回归问题我们可以为每个变量单独拟合一个带惩罚的回归。 lags p_large X_list [] for i in range(1, lags1): X_list.append(df.shift(i)) X pd.concat(X_list, axis1) X.columns [f{col}_lag{i} for i in range(1, lags1) for col in df.columns] X X.iloc[lags:] # 去掉NaN行 y df.iloc[lags:] # 标准化数据对于带L2惩罚的模型很重要 scaler_X StandardScaler() scaler_y StandardScaler() X_scaled scaler_X.fit_transform(X) y_scaled scaler_y.fit_transform(y) # 为每个目标变量拟合 Elastic Net 模型 coefs [] alphas_selected [] for i in range(k): print(f\nFitting model for variable {df.columns[i]}...) # ElasticNetCV 可以交叉验证选择最优的 alpha (正则化强度) 和 l1_ratio (L1/L2混合比) regr ElasticNetCV(l1_ratio[.1, .5, .7, .9, .95, .99, 1], cv5, random_state0, max_iter5000) regr.fit(X_scaled, y_scaled[:, i]) coefs.append(regr.coef_) alphas_selected.append(regr.alpha_) print(f Selected alpha: {regr.alpha_:.4f}, l1_ratio: {regr.l1_ratio_:.2f}) print(f Number of non-zero coefficients: {np.sum(regr.coef_ ! 0)} / {len(regr.coef_)}) # 将系数矩阵重新整理成 VAR 系数矩阵的形式 (k x k*p) coef_matrix np.array(coefs).reshape(k, -1) print(f\nEstimated sparse coefficient matrix shape: {coef_matrix.shape}) # 可以将其分解为 Phi1, Phi2, ..., Phi_p这种方法的价值它自动进行了变量选择。很多滞后变量的系数被压缩为零模型变得稀疏且更易解释。这本质上是估计了一个“稀疏 VAR”模型它是处理高维时间序列最主流、最实用的方法之一。你可以将这个稀疏 VAR 的残差作为后续 MA 部分估计的输入或者直接用它进行预测。5.2 处理更大规模问题的实用建议从 VAR 开始而不是 VARMA在超高维情况下先尝试用带 L1/L2 正则化的 VAR 模型。一个稀疏的高阶 VAR 通常比一个稠密的低阶 VARMA 更实用、更稳定。降维预处理如果变量数量极大如数百个可以先使用主成分分析 (PCA) 或因子模型提取少数几个共同因子对这些因子序列建立 VAR 或 VARMA 模型然后再将结果映射回原始变量空间。利用领域知识限制结构如果你知道变量间的影响存在特定的网络结构或区块结构例如某些变量只影响同一组内的其他变量可以在建模时施加这种约束极大减少参数。关注计算资源对于真正的海量数据T 和 k 都很大你需要考虑分布式计算框架如 Spark MLlib 中的时间序列库或专门的优化库。模型评估重于模型复杂不要一味追求拟合 VARMA。最终目标是良好的样本外预测能力和有经济学意义的系数解释。一个简单但稳健的模型远胜于一个复杂但难以估计、系数无法解释的模型。6. 常见问题排查与经验总结在实际操作中你几乎一定会遇到下面这些问题。6.1 模型估计不收敛或报错问题statsmodels拟合时提示 “Maximum Likelihood optimization failed to converge” 或直接抛出奇异矩阵错误。排查顺序检查数据平稳性这是最常见的原因。对非平稳序列差分后再试。降低模型阶数从 VARMA(1,1) 或甚至 VAR(1) 开始尝试。高阶模型更容易不收敛。提供初始参数statsmodels的VARMAX.fit()方法有start_params参数。你可以先用矩估计或其他简单方法如拟合一个长 VAR得到一组粗糙的参数估计作为 MLE 优化的起点。调整优化器选项尝试fit(method’nm’, maxiter1000)使用 Nelder-Mead 算法它可能比默认的 BFGS 算法更鲁棒但更慢。也可以尝试fit(dispTrue)查看迭代过程看目标函数是否在下降。简化模型考虑去掉移动平均部分 (q0)先拟合 VAR 模型。或者去掉常数项 (trend’n’)。数据尺度如果不同变量的量级差异巨大如 GDP 和利率对数据进行标准化减去均值除以标准差有时能改善数值稳定性。6.2 预测结果非常差或置信区间过宽问题样本外预测的 RMSE 极大或者预测置信区间宽到没有意义。排查顺序检查模型诊断首先回去看残差检验。如果残差不是白噪声说明模型设定错误预测差是必然的。检查结构突变数据可能在训练集和测试集之间发生了根本性变化如政策突变、金融危机。绘制整个序列图观察。如果存在突变需要引入虚拟变量或对突变前后分别建模。模型是否过拟合在训练集上 AIC 很低但在测试集上表现差。尝试使用 BIC 选择更小的阶数或者使用交叉验证。预测步长VARMA 模型适合短期预测。长期预测几十步以上误差会累积置信区间自然会变宽。这是模型本身的局限性。6.3 如何解释系数矩阵问题得到了估计的 (\mathbf{\Phi}_1) 矩阵但不知道如何解读。解读方法(\mathbf{\Phi}_1[i, j]) 表示变量 (j) 的一期滞后值对当期变量 (i) 的直接影响。例如Phi[0,1]0.2表示第二个变量滞后一期对第一个变量有正向影响。但 VARMA 系统的真正影响是动态的、传递的。一个更全面的工具是脉冲响应函数 (IRF)。它描绘了系统中某个变量受到一个单位冲击后对所有变量在未来各期的影响路径。statsmodels的result.irf()可以方便地计算和绘制 IRF。方差分解它告诉你每个变量预测误差的方差有多少比例是由系统内其他变量的冲击引起的。这有助于理解变量的相对重要性。6.4 与机器学习时间序列模型的对比VARMA 的优势模型具有明确的经济或物理意义系数和脉冲响应可以解释。它基于联合概率分布能提供完整的预测分布均值和置信区间。在变量关系稳定、线性假设成立时非常有效。机器学习的优势LSTM、Transformer 等模型能捕捉复杂的非线性关系和超长期依赖。当数据量非常大、且关系高度非线性时它们可能表现更好。但它们通常是“黑箱”解释性差且预测区间难以获得。我的建议不要非此即彼。对于传统的经济、金融、商业预测问题先尝试 VAR/VARMA 这类统计模型。它们原理清晰结果可解释基准性能稳定。只有当统计模型明显表现不佳且你有充足的数据和计算资源时再考虑复杂的深度学习模型。也可以将两者结合例如用 VAR 模型捕捉线性部分用神经网络捕捉残差中的非线性部分。最后留几个我自己在项目中的习惯拿到多变量时间序列数据我的第一反应不是直接调包跑 VARMA。我会先画图看趋势和相关性做平稳性检验。然后一定先从最简单的 VAR(1) 带 L1 正则化开始试看残差。如果残差还行就用它做预测基线。如果残差有很强的模式再考虑增加 VAR 的阶数或引入 MA 项。对于超过 10 个变量的情况稀疏 VAR 几乎总是我的首选。模型的可解释性和稳定性在大多数业务场景下比那一点点预测精度的潜在提升要重要得多。
返回列表