目录
[1. 可视化检查](#1. 可视化检查)
[2. 统计检验:ADF检验(Augmented Dickey-Fuller Test)](#2. 统计检验:ADF检验(Augmented Dickey-Fuller Test))
一、ARIMA是什么?
ARIMA是自回归整合移动平均模型(Autoregressive Integrated Moving Average)的缩写,也被称为Box-Jenkins模型。由统计学家于1970年代提出,专门用于预测平稳或非平稳时间序列。
ARIMA模型的表示形式是:ARIMA(p, d, q),其中:
- p:自回归阶数(AR阶数)
- d:差分阶数(使序列平稳所需的差分次数)
- q:移动平均阶数(MA阶数)
完整表达式为:
二、ARIMA的三个核心组成部分
ARIMA模型由三部分组成:
(1)自回归(AR)- p阶自回归
- 概念:当前值与过去值的线性关系
- 数学表达:
- p阶:表示使用过去多少个值来预测当前值。例如,AR(1)表示当前值与前1期的值有关
(2)差分(I)- d阶差分
- 概念:消除序列中的趋势,使其变平稳
- 差分操作:一阶差分:
;二阶差分:
- d值:需要进行多少次差分才能使序列平稳。d=0:序列已经平稳;d=1:需要一次差分;d=2:需要两次差分。
(3)移动平均(MA)- q阶移动平均
- 概念:当前值与过去误差项 的线性关系。即模型不仅受自身历史值影响,还受过去预测误差的影响。认为"过去的意外冲击会影响未来"。例如,一家餐厅今天的客流量,不仅受昨天客流量(AR部分)影响,还受昨天一个意外事件(如差评或美食博主探店,这相当于预测误差)的影响。
- 数学表达:
- q值:表示使用过去多少个误差项来预测当前值。MA(1)表示当前值与前1期的误差有关。
三、什么是平稳时间序列?
基础定义如下:
平稳时间序列 是指它的统计特性(如均值、方差、自相关性)不随时间变化的序列。
之所以需要使用平稳时间序列,是因为我们的核心假设是:未来的模式 = 过去的模式,ARIMA模型的核心思想就是:先让序列变平稳,再用过去的规律预测未来。如果序列是非平稳的(比如一直在上涨),即统计规律是不稳定的,那么"过去"的规律可能在未来不再适用。
✅ 图示特征:
- 没有明显的上升或下降趋势
- 波动幅度大致相同(不会越来越"炸"或越来越"窄")
- 数据在一条水平线附近徘徊
✅平稳序列的例子:
- 白噪声(纯随机波动)
- 围绕某个固定水平上下波动的数据(比如每天室温在25°C附近随机波动)
- 经过处理后去除趋势和季节性的经济指标
数学上的严格定义(弱平稳/二阶平稳):
一个时间序列
是平稳的,如果满足以下三个条件:
- 均值恒定且有限 :
(对所有 t 都一样)
- 方差恒定且有限 :
(波动大小不变)
- 自协方差只与时间间隔有关 :
(只取决于间隔 k,不取决于具体时间 t)
关于第3条,举一个例子说明。想象你在一条平稳的河流上测量水位:
- 某天上午10点 vs 11点:水位相关性强
- 三个月后某天上午10点 vs 11点:相关性一样强
- 因为河流没有涨潮/枯水季(无趋势、无季节性)
但如果是在雨季 vs 旱季:
- 雨季时水位剧烈波动,相邻小时高度相关
- 旱季时水位平稳,相邻小时几乎无关→ 相关性随时间 t 变化 → 非平稳
为什么这个性质重要?因为ARIMA 模型要估计"过去如何影响未来",比如:"昨天比平均高,今天会不会也高?"如果这种关系今年和十年前不一样,那模型就无法泛化。
四、为什么差分方法能够得到平稳时间序列?
差分 就是计算相邻时间点的变化量。
比如,一阶差分**** 表示"今天比昨天增加了多少", 假设有个带趋势的时间序列
,
是白噪声,通过做一阶差分后
,均值变成了常数2,波动由噪声差决定,变成平稳序列!
再比如,二阶差分表示"增长速度的变化"。假设销售额第一年从10 → 15(+5),第二年15 → 22(+7),第三年22 → 31(+9),第四年31 → 42(+11),即增长量本身在增加,这是二次趋势,比线性趋势"更陡",二次差分后就会平稳。
假设真实模型为:
-
一阶差分:
仍然是 关于 t 的一次函数(线性趋势),所以非平稳。
-
二阶差分:
综上,差分原理就是把"水平值"变成"变化量",从而剥离掉趋势成分,只保留围绕某个均值的随机波动。如果N次差分不够,那就N+1次差分!
| 非平稳类型 | 差分是否有效? | 说明 |
|---|---|---|
| 线性趋势 | ✅ 一阶差分通常足够 | 如 GDP、人口增长 |
| 二次趋势(曲线) | ✅ 需要二阶差分 | 如加速增长的科技 adoption |
| 季节性 | ❌ 普通差分效果有限 | 需要用季节性差分(如12阶差分处理月度季节性) |
| 方差不稳定 | ❌ 差分无效 | 需要用对数变换或Box-Cox变换 |
五、ARIMA模型的构建步骤(六步法)
- 平稳性检验:检查序列是否平稳
- 差分处理:如果序列非平稳,进行差分操作,通过观察差分后序列的平稳性确定d值
- 模型定阶:ACF&PACF确定p和q的值
- 参数估计:使用最大似然估计等方法估计模型参数,通常使用Python的statsmodels库或R的forecast包自动完成
- 残差检验:检查残差是否为白噪声,如果残差不是白噪声,需要重新调整模型
- 预测应用:使用最优模型进行未来值的预测,生成预测区间,评估预测的不确定性
python
# 导入必要的库
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from statsmodels.tsa.arima.model import ARIMA
from statsmodels.tsa.stattools import adfuller
# 加载数据(假设数据是时间序列)
# df = pd.read_csv('data.csv')
# df['date'] = pd.to_datetime(df['date'])
# df = df.set_index('date')
# 检查平稳性
result = adfuller(df['value'])
print('ADF Statistic:', result[0])
print('p-value:', result[1])
# 如果p-value > 0.05,序列非平稳,需要差分
# 进行差分处理
df['diff'] = df['value'].diff().dropna()
# 重新检查平稳性
result = adfuller(df['diff'])
print('ADF Statistic (after diff):', result[0])
print('p-value (after diff):', result[1])
# 自动确定ARIMA参数
# 使用auto_arima函数(需要安装pmdarima库)
# from pmdarima import auto_arima
# model = auto_arima(df['value'], seasonal=False, trace=True)
# 或者手动选择参数
model = ARIMA(df['value'], order=(1, 1, 1))
results = model.fit()
# 查看模型摘要
print(results.summary())
# 进行预测
forecast = results.get_forecast(steps=5)
forecast_values = forecast.predicted_mean
forecast_conf_int = forecast.conf_int()
# 绘制预测结果
plt.figure(figsize=(12,6))
plt.plot(df.index, df['value'], label='Actual')
plt.plot(forecast_values.index, forecast_values, label='Forecast', color='red')
plt.fill_between(forecast_conf_int.index, forecast_conf_int.iloc[:,0], forecast_conf_int.iloc[:,1], color='pink', alpha=0.5)
plt.legend()
plt.show()
ARIMA模型是时间序列分析的基础工具,特别适合处理有趋势但没有复杂模式的非平稳时间序列。ARIMA的缺点:
- 无法处理非线性关系:如果数据有很强的非线性特征,ARIMA效果可能不好
- 长期预测效果不佳:ARIMA更适合短期预测
- 参数选择复杂:需要经验或工具来确定p、d、q
- 对异常值敏感:数据中的异常点可能影响模型效果
六、一些统计检验或技术处理
(一)平稳性检验
1. 可视化检查
- 画出差分后的序列图
- 看是否还在明显上升/下降?波动是否稳定?
2. 统计检验:ADF检验(Augmented Dickey-Fuller Test)
- 原假设 H_0:序列非平稳(有单位根)
- 备择假设 H_1:序列平稳
python
from statsmodels.tsa.stattools import adfuller
result = adfuller(series)
print('ADF Statistic:', result[0])
print('p-value:', result[1])
- 如果 p-value < 0.05 → 拒绝原假设 → 序列平稳
- 如果 p-value ≥ 0.05 → 不能拒绝原假设 → 序列非平稳 ,需要继续差分
ADF 检验通过判断"这个序列是否存在单位根(unit root)?"来判断序列是否平稳, "存在单位根" ⇨ 非平稳 ;"不存在单位根" ⇨ 平稳。
什么是"单位根"?简单理解:
- 单位根 是导致时间序列非平稳的一种数学结构。
- 最典型的例子:随机游走(Random Walk)
随机游走模型:, 其中
是白噪声。
这个序列:
- 每一步都"继承"上一步的值 + 随机扰动
- 会不断漂移,没有固定均值
- 是非平稳的!
而它的特征方程有一个根等于 1 → 称为"单位根"。
🔑 关键结论 :
如果一个序列有单位根 → 它是非平稳的(至少需要差分一次)。
(二)模型定阶ACF&PACF
方法:观察自相关函数(ACF)和偏自相关函数(PACF)图
下面讲一下这个方法背后的原理:
自相关函数(ACF - Autocorrelation Function)
-
定义:衡量时间序列与其自身滞后版本之间的相关性
-
简单理解 :ACF(k)表示当前观测值
与k期前的观测值
之间的相关性
-
特点 :包含了直接和间接的相关性
偏自相关函数(PACF - Partial Autocorrelation Function)
-
定义:在控制中间滞后项影响后,当前观测值与滞后观测值之间的直接相关性
-
简单理解 :PACF(k)表示
与
之间的"纯净"相关性,剔除了
的影响
-
特点 :只测量直接相关性
案例1:纯AR(1)模型特征
假设我们有一个AR(1)模型:
ACF图特征:
-
滞后1期:0.8(显著)
-
滞后2期:0.8² = 0.64(显著)
-
滞后3期:0.8³ = 0.512(显著)
-
以此类推,即ACF拖尾(逐渐衰减)
PACF图特征:
-
滞后1期:0.8(显著)
-
滞后2期:接近0(不显著,因为控制
后,
与
无直接关系)
-
滞后3期及以后:都不显著
-
以此类推,即PACF在滞后1期后"截尾"
案例2:纯MA(1)模型特征
MA(1)模型的一般形式为:
其中:
-
μ是常数项(通常假设为0,或通过去均值处理)
-
是白噪声,满足
-
之间相互独立:
为简化推导,我们假设 μ=0
特征1:纯MA(1)会在ACF图上第1期截尾,滞后2期及以后都为0。证明如下。
- 计算方差
- 计算自协方差
同理计算自协方差
即,对于所有 k≥2,都有。
- 求自相关系数:
特征2:纯MA(1)会在PACF图上拖尾衰减。证明如下。
对于MA(1)模型,可以将其转换为AR(∞)形式来理解,即Yule-Walker方程。
这是一个AR(∞)过程,滞后1项系数; 滞后2项系数
;滞后3项系数
。当∣θ∣<1(对于可逆的MA模型),这些值按指数衰减到0
判断规则总结
综上所述,判断标准表格为:
| 模型类型 | ACF特征 | PACF特征 | 建议(p,d,q) |
|---|---|---|---|
| AR(p) | 衰减到0(拖尾) | 在p阶后截尾 | (p, d, 0) |
| MA(q) | 在q阶后截尾 | 衰减到0(拖尾) | (0, d, q) |
| ARMA(p,q) | 衰减到0(拖尾) | 衰减到0(拖尾) | (p, d, q) |
python
# Python示例代码
import pandas as pd
import matplotlib.pyplot as plt
from statsmodels.graphics.tsaplots import plot_acf, plot_pacf
from statsmodels.tsa.stattools import adfuller
# 绘制ACF和PACF图
plt.figure(figsize=(12, 6))
# ACF图
plt.subplot(1, 2, 1)
plot_acf(stationary_data, lags=40, ax=plt.gca())
plt.title('自相关函数(ACF)')
plt.xlabel('滞后阶数')
# PACF图
plt.subplot(1, 2, 2)
plot_pacf(stationary_data, lags=40, ax=plt.gca(), method='ols')
plt.title('偏自相关函数(PACF)')
plt.xlabel('滞后阶数')
plt.tight_layout()
plt.show()
(三)残差检验方法
如果一个模型很好地拟合了数据,那么它的残差应该是白噪声 :均值为0、方差恒定、没有自相关性、正态分布(理想情况)。Ljung-Box检验专门检验第三个条件:残差是否没有自相关性。
如果模型的残差仍然有规律(例如,今天的正残差往往跟着明天的正残差),这意味着模型没有捕捉到所有的信息,还有改进的空间(可能需要增加模型阶数)。
你可能问:"为什么不用ACF图直接看?"因为ACF图是视觉判断 ,主观性强,而Ljung-Box检验提供客观的统计判断,特别是在边界情况下(自相关接近但不超出置信区间),统计检验更可靠。
Ljung-Box检验统计量定义为:
其中:
-
:样本大小
-
:检验的滞后阶数(通常取
或 20)
-
:残差在滞后阶数 k 的样本自相关系数
-
:服从自由度为m 的卡方分布
滞后阶数m的选择
-
经验法则 :通常取
,其中n是样本量
-
常用值:10, 15, 20是常见选择
-
多滞后检验:同时检验多个m值更可靠
代码如下:
python
# 3. 残差的ACF图
from statsmodels.graphics.tsaplots import plot_acf
plot_acf(residuals, lags=20, ax=axes[1, 0])
axes[1, 0].set_title('残差的ACF图')
# 4. Q-Q图(检验正态性)
from scipy import stats
stats.probplot(residuals, dist="norm", plot=axes[1, 1])
axes[1, 1].set_title('Q-Q图')
plt.tight_layout()
plt.show()
# 进行Ljung-Box检验
print("\n=== Ljung-Box检验结果 ===")
# 方法1:使用acorr_ljungbox函数
lb_test = acorr_ljungbox(residuals, lags=[10, 15, 20], return_df=True)
print("Ljung-Box检验统计量:")
print(lb_test)
# 方法2:手动计算并解释
print("\n=== 检验结果解释 ===")
for lag in [10, 15, 20]:
lb_stat, p_value = acorr_ljungbox(residuals, lags=[lag], return_df=False)
print(f"滞后{lag}阶: Q统计量 = {lb_stat[0]:.4f}, p值 = {p_value[0]:.4f}", end=" ")
if p_value[0] > 0.05:
print("✓ 不能拒绝原假设,残差是白噪声")
else:
print("✗ 拒绝原假设,残差存在自相关")