前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >时间序列平稳性检验方法(Python)

时间序列平稳性检验方法(Python)

作者头像
Python数据科学
发布2024-03-05 13:29:36
2630
发布2024-03-05 13:29:36
举报
文章被收录于专栏:Python数据科学Python数据科学

作者:东哥起飞,来源:Python数据科学

当我们拿到时序数据后,首先要进行平稳性和纯随机性的检验,这两个重要的检验是时间序列的预处理。根据检验的结果可以判断出序列属于什么类型,然后对症下药使用相应的分析方法。

本篇讲解平稳性的检验方法。平稳性检验方法可分为两个类,一种是比较直观的画图,根据 ACF 和 PACF 的可视化图判断时序平稳性;另一种是量化的方法,通过假设检验计算结果来准确判断。

自相关图可视化

该方法主要通过 ACF 和 PACF 自相关可视化图来辅助判断,较为常用。

关于自相关的概念可以参考这篇 时间序列 ACF 和 PACF 理解、代码、可视化

先抛出判断标准:平稳序列通常具有短期相关性,即随着滞后期数

k

增加,平稳序列的自相关系数会很快地向零衰减,而非平稳时序的自相关系数向零衰减的速度比较慢。

下面我直接通过Python代码可视化的案例说明如何通过自相关辅助判断,分别模拟出了白噪声、非白噪声平稳时序、非平稳时序、随机游走四种时序。

代码语言:javascript
复制
import numpy as np
import pandas as pd
from matplotlib import pyplot as plt
import warnings
warnings.filterwarnings("ignore")

# 白噪声
white_noise = np.random.standard_normal(size=500)

# 随机游走
np.random.seed(6)
def random_walk():
    steps = np.random.standard_normal(size=500)
    steps[0] = 0
    walk = np.cumsum(steps)
    return walk

# 模拟时序
def simulate_process(is_stationary:bool)->np.array:
    np.random.seed(42)
    process=np.empty(100)

    if is_stationary:
        alpha=0.5
        process[0]=0
    else:
        alpha=1
        process[0]=10
    for i in range(100):
        if i+1<100:
            process[i+1]=alpha*process[i]+np.random.standard_normal()
        else:
            break
    return process

# 非平稳时序
non_stationary=simulate_process(False)

# 非白噪声的平稳时序
yes_stationary=simulate_process(True)


fig, ((ax1, ax2), (ax3, ax4)) = plt.subplots(2, 2, figsize=(15, 8))
# fig.subplots_adjust(hspace=0.5)
ax1.plot(white_noise)
ax1.set_title('white_noise')
ax2.plot(random_walk())
ax2.set_title('random_walk')
ax3.plot(yes_stationary)
ax3.set_title('yes_stationary')
ax4.plot(non_stationary)
ax4.set_title('non_stationary')
plt.show()

通过 statsmodels 分别绘制4个时序的 ACF 和 PACF 图。

代码语言:javascript
复制
from statsmodels.graphics.tsaplots import plot_acf, plot_pacf

fig, ax = plt.subplots(4, 2, figsize=(15, 12))
fig.subplots_adjust(hspace=0.5)

plot_acf(white_noise, lags=40, ax=ax[0][0])
ax[0][0].set_title('ACF(white_noise)')
plot_pacf(white_noise, lags=40, ax=ax[0][1])
ax[0][1].set_title('PACF(white_noise)')

plot_acf(random_walk(), lags=40, ax=ax[1][0])
ax[1][0].set_title('ACF(random_walk)')
plot_pacf(random_walk(), lags=40, ax=ax[1][1])
ax[1][1].set_title('PACF(random_walk)')

plot_acf(yes_stationary, lags=40, ax=ax[2][0])
ax[2][0].set_title('ACF(yes_stationary)')
plot_pacf(yes_stationary, lags=40, ax=ax[2][1])
ax[2][1].set_title('PACF(yes_stationary)')

plot_acf(non_stationary, lags=40, ax=ax[3][0])
ax[3][0].set_title('ACF(non_stationary)')
plot_pacf(non_stationary, lags=40, ax=ax[3][1])
ax[3][1].set_title('PACF(non_stationary)')
plt.figure(figsize=(20, 6))
plt.show()

白噪声:0时刻ACF为1,相当于自己和自己本身的相关性,这个不难理解,而非0时刻的滞后期ACF迅速退化到0附近,PACF 也是同样的形态,是典型的平稳序列,可见白噪声0时刻与滞后期时序几乎没有相关性,即无法根据历史数据预测未来。

随机游走:0时刻ACF为1,滞后期的ACF整体成下降趋势,但退化非常缓慢,0时刻与滞后40期的相关性仍有0.8左右。由于随机游走每一次的变化都是在上一次基础上累加的,所以相关性很强,滞后k期的ACF退化的非常慢。而PACF图中,滞后1期与0时刻相关性均为1,剩余滞后期迅速退化为0附近。这是因为滞后1期时序是在0时刻基础上随机的,相关性极高,而剩余滞后期时序考虑PACF概念(排除了其他滞后期时序的干扰,仅考虑自身与0时刻的相关性),那就变成随机的白噪声了。

非白噪声平稳时序: 正常平稳时序具体短期相关性的特点,ACF图中相关性在滞后1期以后降到0附近并保持在2倍标准差内窄幅震荡,这是随机性很强的平稳时序特征。与白噪声的区别是,白噪声虽也是平稳时序但从0时刻后就迅速降到0,是毫无相关性的。

非平稳时序: ACF相关性下降非常缓慢,很很长的滞后期里,自相关系数一直为正,随后又一直为负,显示出明显的三角对称性,这是具有单调趋势的非平稳序列的典型特征。

以上是根据自相关图特征进行的判断,关于这几种时序的概念和介绍可以参考:时间序列平稳性、白噪声、随机游走

自相关图的判断方法可以总结为以下几个特点。

  • 单调性:ACF衰减到0的速度很慢,而且可能一直为正,或一直为负,或先正后负,或先负后正。
  • 周期性:ACF呈正弦波动规律。
  • 平稳性:ACF衰减到0的速度很快,并且十分靠近0,并控制在2倍标准差内。

假设检验

自相关图判断时序是否平稳的缺点是会带有主观色彩,所以一般还会通过假设检验的量化方法进行验证,假设检验的方法更为准确。

目前假设检验的主流方法是单位根检验,检验序列中是否存在单位根,如存在,则为平稳时序,如存在则为平稳时序。

什么是单位根检验?

我们看下面这个模型,如果将

\beta_1

去掉,就等于随机游走序列。

y_t = \beta_1 y_{t-1} + \varepsilon_t

,其中

\{\varepsilon_t\}

为白噪声。

现在

\beta_1

的不同取值会直接影响到该序列是否平稳,有以下几种情况:

|\beta_1|<1

:随着

t

增大

y_t

最终会收敛,长期来看

\{y_t\}

是平稳的

\beta_1=1

\{y_t\}

是非平稳的随机游走序列

\beta_1>1

\{y_t\}

是爆炸式增长的更非平稳序列

以上第二种情况

\beta_1=1

就是所谓的单位根,是差分方程正好落在单位圆上的特征根

\lambda=1

单位根检验就是检验差分方程的特征方程的各个特征根

\lambda

是均小于1,还是存在等于1的情况。由于日常数据中基本不存在单位根均大于1的情况,所以只需检验单位根小于1还是等于1。

ADF检验

ADF检验是目前最常用的单位根假设检验方法,它对DF检验进行了修正,由仅考虑一阶自回归的DF检验拓展到了适用于高阶自回归的平稳性检验。其定义如下:

对任一

AR(p)

过程:

x_t=\phi_1x_{t-1}+...+\phi_px_{t-p}+\varepsilon_t

它的特征方程为:

\lambda^p-\phi_1\lambda^{p-1}-...-\phi_p=0

如果该方程所有特征根都在单位圆内,即

|\phi_i|<1,i=1,2,...,p

,则序列

\{x_t\}

平稳。

如果有一个特征根存在,即

\lambda_i=1

,则:

\lambda^p-\phi_1\lambda^{p-1}-...-\phi_p=0
\Longrightarrow1-\phi_{1}-...-\phi_{p}=0
\Longrightarrow \phi_{1}+\phi_{2}+...+\phi_{p}=1

\rho=\phi_{1}+\phi_{2}+...+\phi_{p}-1

因此假设条件为:

  • 原假设:
H_0:\rho=0

,即存在单位根,假设时序是非平稳的(因为生活中大多数的时序都是非平稳的,所以原假设为非平稳)

  • 备择假设:
H_1:\rho<0

,即不存在单位根

下面使用arch包实现一个ADF检验过程。首先构造一个非平稳时序。

代码语言:javascript
复制
# 构建一个非平稳时序
import numpy as np
from matplotlib import pyplot as plt

np.random.seed(1)

y = np.random.standard_normal(size=100)
for i in range(1, len(y)):
    y[i] = 1 + 0.2*i + y[i]

plt.figure(figsize=(12, 6))
plt.plot(y)
plt.show()
代码语言:javascript
复制
from arch.unitroot import ADF
# 非趋势项非截距项平稳性检验
adf = ADF(y)
print(adf.summary().as_text())

# 趋势平稳检验
adf = ADF(y,trend = 'ct')
print(adf.summary().as_text())

arch包可以设置参数trend参数,根据要检验的平稳类型可以选择不包含趋势项n、包含截距项c、包含截距项和趋势项ct、包含截距项和趋势项和二次趋势项ctt,默认值为c

第一次ADF检验trend为默认值c包含截距项,即检验含截距项是否平稳,

p=0.755>0.05

,不能拒绝原假设,故序列非平稳。

第一次ADF检验trend为ct包含截距项和趋势项,即验证含截距项和趋势项是否平稳,

p=0<0.05

,拒绝原假设,序列为趋势项平稳。

PP检验

ADF检验主要适用于方差齐性场合,对于异方差序列的平稳性检验效果不佳。Phillips和Perron(1988) 提出了一种非参数检验方法,对ADF检验进行了非参数修正,既可适用于异方差场合,又服从ADF检验统计量极限分布。假设条件一样,与ADF用法相似,可作为ADF检验的补充。

代码实现如下,仍用前面构造的非平稳时序为例。

代码语言:javascript
复制
import numpy as np
from arch.unitroot import PhillipsPerron
# 非趋势项非截距项平稳性检验
pp = PhillipsPerron(y)
print(pp.summary().as_text())
# 趋势平稳检验
pp = PhillipsPerron(y,trend = 'ct')
print(pp.summary().as_text())

第一次PP检验trend为默认值c包含截距项,即检验含截距项时序是否平稳,

p=0.951>0.05

,不能拒绝原假设,故序列非平稳。

第一次PP检验trend为ct包含截距项和趋势项,即验证含截距项和趋势项是否平稳,

p=0<0.05

,拒绝原假设,序列为趋势项平稳。

综合ADF检验和PP检验两种方法,以上构造的时序可以判定为趋势平稳的。

除了以上两种检验方法,还有DF-GLS检验、KPSS检验、Zivot-Andrews检验、Variance Ratio检验等方法,不做详细介绍,代码实现同样可以通过arch包调用。

参考链接 [1].《应用时间序列分析》王燕 [2].https://mp.weixin.qq.com/s/4M8ayYaghstPFURKybvARA [3].https://mp.weixin.qq.com/s/vgzAbeLWDdRv2YbRXydg8g [4].https://github.com/bashtage/arch [5].https://mp.weixin.qq.com/s/QVziYRaNAqiHDqNTR60Fsw

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2024-03-04,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Python数据科学 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 自相关图可视化
  • 假设检验
    • ADF检验
      • PP检验
      相关产品与服务
      灰盒安全测试
      腾讯知识图谱(Tencent Knowledge Graph,TKG)是一个集成图数据库、图计算引擎和图可视化分析的一站式平台。支持抽取和融合异构数据,支持千亿级节点关系的存储和计算,支持规则匹配、机器学习、图嵌入等图数据挖掘算法,拥有丰富的图数据渲染和展现的可视化方案。
      领券
      问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档