手把手教你用Python处理非平稳时间序列

简介

预测一个家庭未来三个月的用电量,估计特定时期道路上的交通流量,预测一只股票在纽约证券交易所交易的价格……这些问题都有什么共同点?

它们都属于时间序列数据的范畴!如果没有“时间”成分,就无法准确地预测出结果。随着我们周围世界产生的数据越来越多,时间序列预测已成为数据科学家必须掌握的一项越来越关键的技能。

然而,时间序列是一个复杂的话题,它具有多面性。

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

首先,要想使预测模型正常工作,就必须使时间序列保持平稳。为什么?因为绝大部分原始数据都会有非平稳的趋势。如果有很多不规则的尖峰,你怎么能确保模型正常工作呢?

本文将重点介绍时间序列数据的平稳性检验方法。在此假设读者已熟悉时间序列、ARIMA和平稳性的概念,以下是一些包含基础内容的参考资料:

  • 时间序列建模完整教程
  • 给初学者的时间序列预测综合指南

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

1. 平稳简介

“平稳”是处理时间序列数据时遇到的最重要的概念之一:平稳序列是指其特性-均值、方差和协方差不随时间而变化的序列。

让我们用一个直观的例子来理解这一点。考虑以下三个图形:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

  • 在第一幅图中,我们可以清楚地看到,均值随时间而变化(增加),呈现上升的趋势。因此,这是一个非平稳序列。平稳序列不应该呈现出随时间变化的趋势。
  • 第二幅图显然看不到序列的趋势,但序列的变化是一个时间的函数。正如前面提到的,平稳序列的方差必须是一个常数。
  • 再来看第三幅图,随着时间的增加,序列传播后变得更近,这意味着协方差是时间的函数。

上述三个例子均是非平稳时间序列。现在来看第四个图:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

在这张图中,均值、方差和协方差都是常数,这就是平稳时间序列。

再想一想,上面的哪一幅图预测未来会更容易呢?第四个图,对吧?大多数统计模型都要求序列是平稳的,这样才能进行有效和精确的预测。

因此,总的来说,平稳时间序列是一个不依赖时间变化 (即均值、方差和协方差不随时间变化)的时间序列。在下一节中,我们将介绍各种检测给定序列是否平稳的方法。

2. 加载数据

在本节和后续几节中,将介绍检测时间序列数据的平稳性的方法,以及如何处理非平稳序列。同时,本文还提供了相应的Python代码。大家可以到:AirPassengers下载文中使用的数据集。

在继续分析数据集之前,首先加载和预处理数据。

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列
《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

好了,看来可以继续了!

3. 检验平稳的方法

下一步是确定给定的序列是否是平稳的,并对它做相应的处理。本节将介绍一些常见的方法,利用这些方法来检测序列是否平稳。

目视检验

看一下我们在上一节中使用的图形,仅需通过目测图形,便能够识别出序列的均值和方差是否随时间变化。同样,通过绘制数据图形,便能确定该序列的属性是否随时间而变化。

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列
《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

显然,通过作图,可以看到序列的趋势(变化的均值),然而,这种目视检测方法得到的结果可能不准确。最好是用一些统计检验方法来验证观测结果。

统计检验

可以利用统计检验来代替目视检验:比如单位根平稳检验。单位根表名给定序列的统计特性(均值,方差和协方差)不是时间的常数,这是平稳时间序列的先决条件。下面是它的数学解释:

假设我们有一个时间序列:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

其中yt是t时刻的数据值,ε t 是误差项。需要利用yt-1的值来计算yt,即:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

如果利用所有的观察值,yt 的值将是:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

假设在上述方程中a的值为1(单位),则预测值将等于yt-n 和从t-n到t的所有误差之和,这意味着方差将随着时间的推移而增大,这就是时间序列中的单位根。众所周知,平稳时间序列的方差不能是时间的函数。单元根检验通过检查a=1的值来检查序列中是否存在单位根。以下是两个最常用的单位根平稳检测方法:

ADF(增补迪基-福勒)检验The Dickey Fuller test is one of the most popular statistical tests. It can be used to determine the presence of unit root in the series, and hence help us understand if the series is stationary or not. The null and alternate hypothesis of this test are:

迪基-福勒(Dickey Fuller)检验是最流行的统计检验方法之一,可以用它来确定序列中单位根的存在,从而帮助判断序列是否是平稳。这一检验的原假设与备择假设如下:

原假设:序列有一个单位根(a=1的值)

备择假设:该序列没有单位根。

如果不能拒绝原假设,则该序列是非平稳的,这意味着序列可以是线性的,也可以是差分平稳的(将在下一节中更多地了解差分平稳)。

Python代码:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

ADF检验结果:ADF检验的统计量为1%,p值为5%,临界值为10%,置信区间为10%。我们对本序列的检验结果如下:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

平稳性检验:如果检验统计量小于临界值,我们可以拒绝原假设(也就是序列是平稳的)。当检验统计量大于临界值时,不能拒绝原假设(这意味着序列不是平稳的)。

在上面的例子中,检验统计量>临界值,这意味着序列不是平稳的。这证实了我们最初在目视检测中观察的结果。

KPSS(科瓦特科夫斯·基菲利普·斯施密特·辛)检验KPSS检验是另一种用于检查时间序列的平稳性 (与迪基-福勒检验相比稍逊一筹) 的统计检验方法。KPSS检验的原假设与备择假设与ADF检验的原假设与备择假设相反,常造成混淆。

KPSS检验的作者将原假设定义为趋势平稳,并将备择假设定义为单位根序列。我们将在下一节详细了解趋势平稳。现在,来看一下KPSS检验的实现,并查看KPSS检验的结果。

原假设:序列是趋势平稳的。

备择假设:序列有一个单位根(序列是非平稳的)。

Python代码:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

KPSS检验结果:KPSS检验-检验统计量、p-值和临界值和置信区间分别为1%、2.5%、5%和10%。对于航空乘客数据集的检验结果如下:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

平稳性检验:如果检验统计量大于临界值,则拒绝原假设(序列不是平稳的)。如果检验统计量小于临界值,则不能拒绝原假设(序列是平稳的)。对于航空乘客数据集来说,在所有置信区间,检验统计量的值都大于临界值,因此可以说该序列是不平稳的。

在为时间序列数据集准备模型之前,通常会同时进行两种检验。有一次,这两种检验显示出相互矛盾的结果:其中一个检验结果表明该序列是平稳的,而另一个则表明该序列是非平稳的!我困惑了好几个小时,想弄清楚这是怎么回事。后来才知道,序列的平稳性有多种类型。

综上所述,ADF检验有线性平稳或差分平稳的备择假设,而KPSS检验则是识别序列的趋势平稳。

4. 平稳的种类

通过了解不同类型的平稳,来解释上述检验的结果。

  • 严格平稳:严格平稳序列满足平稳过程的数学定义。严格平稳序列的均值、方差和协方差均不是时间的函数。我们的目标是将一个非平稳序列转化为一个严格平稳序列,然后对它进行预测。
  • 趋势平稳:没有单位根但显示出趋势的序列被称为趋势平稳序列。一旦去除趋势之后,产生的序列将是严格平稳的。在没有单位根的情况下,KPSS检测将该序列归类为平稳。这意味着序列可以是严格平稳的,也可以是趋势平稳的。
  • 差分平稳:通过差分可以使时间序列成为严格平稳的时间序列。ADF检验也称为差分平稳性检验。

应用两种检验总会更优些,通过两种检验之后,可以确定这个序列是否是平稳的。下面,来看一下应用两种平稳检验后的可能结果:

  • 结果1:两种检验均得出结论:序列是非平稳的->序列是非平稳的
  • 结果2:两种检验均得出结论:序列是平稳的->序列是平稳的
  • 结果3:KPSS =平稳;ADF =非平稳->趋势平稳,去除趋势后序列严格平稳
  • 结果4:KPSS =非平稳;ADF =平稳->差分平稳,利用差分可使序列平稳。

5. 时间序列的平稳化

在熟悉了平稳性的概念及其不同的类型之后,接下来可以对序列进行平稳化操作。请记住,为了建立时间序列预测模型,必须首先将任何非平稳序列转换为平稳序列。

差分化

在该方法中,计算序列中连续项的差值。执行差分操作通常是为了消除均值的变化。从数学角度,差分可以写成:

yt‘ = yt – y(t-1)

其中yt 是t时刻的数值。

对序列差分化后,绘制出结果:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列
《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

季节性差分

在季节性差分中,不计算连续值之间的差异,而是计算观察值与同一季节的先前观察值之间的差异。例如,星期一的观察值将与上星期一的观察值相减。从数学角度,它可以写成:

yt‘ = yt – y(t-n)

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

变换

变换用于对方差为非常数的序列进行平稳化。常用的变换方法包括幂变换、平方根变换和对数变换。对飞机乘客数据集进行快速对数转换和差分:

《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列
《手把手教你用Python处理非平稳时间序列》 手把手教你用Python处理非平稳时间序列

可以看出,这个图形比先前的图形有了很大的改善。通过对这个序列进行平方根或幂变换,看看是否得出了更好的结果。欢迎在下面的评论里分享你的发现!

尾注

本文介绍了检验时间序列平稳性的不同方法。但并不止步于此,下一步是对得到的序列应用一个预测模型。可以参考以下文章来构建这样的模型:给初学者的时间序列预测综合指南(Beginner’s Guide to Time Series Forecast)。

    原文作者:妄心xyx
    原文地址: https://www.jianshu.com/p/2c55371f5769
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞