python - 这个时间序列是否平稳?

标签 python r time-series statsmodels arima

我想检查保存在 TS.csv 中的时间序列数据的平稳性.

但是,R 的 tseries::adf.test() 和 Python 的 statsmodels.tsa.stattools.adfuller() 给出完全不同的结果。

adf.test() 显示它是平稳的 (p < 0.05),而 adfuller() 显示它是非平稳的 (p > 0.05)。

下面的代码有没有问题?

在 R 和 Python 中测试时间序列平稳性的正确过程是什么?

谢谢。

R 代码:

> rd <- read.table('Data/TS.csv', sep = ',', header = TRUE)
> inp <- ts(rd$Sales, frequency = 12, start = c(1965, 1))
> inp
     Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec
1965 154  96  73  49  36  59  95 169 210 278 298 245
1966 200 118  90  79  78  91 167 169 289 347 375 203
1967 223 104 107  85  75  99 135 211 335 460 488 326
1968 346 261 224 141 148 145 223 272 445 560 612 467
1969 518 404 300 210 196 186 247 343 464 680 711 610
1970 613 392 273 322 189 257 324 404 677 858 895 664
1971 628 308 324 248 272
> library(tseries)
> adf.test(inp)

    Augmented Dickey-Fuller Test

data:  inp
Dickey-Fuller = -7.2564, Lag order = 4, p-value = 0.01
alternative hypothesis: stationary

Python 代码(来自 Time_Series.ipynb ):

import pandas as pd
from statsmodels.tsa.stattools import adfuller
df = pd.read_csv('Data/TS.csv')
ts = pd.Series(list(df['Sales']), index=pd.to_datetime(df['Month'],format='%Y-%m'))
s_test = adfuller(ts, autolag='AIC')
print("p value > 0.05 means data is non-stationary: ", s_test[1])
# output: p value > 0.05 means data is non-stationary:  0.988889420517

更新

@gfgm 很好地解释了为什么 R 和 Python 的结果不同,以及如何通过更改参数使它们相同。

对于上面的第二个问题:“在 R 和 Python 中测试时间序列的平稳性的正确过程是什么?”。 我想提供一些细节:

当预测一个时间序列时,ARIMA 模型需要输入的时间序列是平稳的。 如果输入不是静止的,它应该是 log()ed 或 diff()ed 以使其静止, 然后将其拟合到模型中。

所以问题是: 我是否应该认为输入是固定的(使用 R 的默认参数)并将其直接拟合到 ARIMA 模型中, 或者认为它是非固定的(使用 Python 的默认参数), 并使用额外的函数(如 log()diff())使其静止不动?

最佳答案

结果不同是因为拟合的模型略有不同,而且模型的滞后阶数完全不同。 python 测试包括一个常量“漂移”项(估计一个常量,从而使时间序列以零为中心),但 R 测试包括一个常量和一个线性趋势项。这可以在 python 代码中使用参数 regression = 'ct' 指定。

r 中的默认滞后长度

nlag = trunc((length(x)-1)^(1/3))

python 中的默认滞后长度

12*(nobs/100)^(1/4)

当您运行 Python 代码时,您告诉函数根据 AIC 标准选择最佳滞后长度。如果我们告诉 python 运行一个居中和去趋势的模型,并且我们告诉它使用 R 滞后长度标准,我们得到:

In [5]: adfuller(ts, regression="ct", maxlag = 4)[1]
Out[5]: 3.6892966741832268e-09

很难看出这是否与 R 的结果相同,因为 R 将其 p 值四舍五入为 .01,但我们可以告诉 R 使用 python 的滞后长度,而 python 使用 R 的模型(我不能更改模型R 具有此功能)。我们得到:

adf.test(inp, k = ceiling(12*(length(inp)/100)^(1/4)))

    Augmented Dickey-Fuller Test

data:  inp
Dickey-Fuller = -2.0253, Lag order = 12, p-value = 0.5652
alternative hypothesis: stationary

在 python 中:

In [6]: adfuller(ts, regression="ct")[1]
Out[6]: 0.58756464088883864

不完美,但非常接近。

备注:

python 模型的实际 Dickey-Fuller 测试统计量是

In [8]: adfuller(ts, regression="ct")[0]
Out[8]: -2.025340637385288

这与 R 结果相同。这些测试可能使用不同的方式从统计数据中计算 p 值。

关于python - 这个时间序列是否平稳?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49505749/

相关文章:

Python平滑时间序列数据

python - 如何为 Windows 构建 SystemTray 应用程序?

python - Pandas 中的 loc 函数

javascript - 使用python从网站获取音频源链接

r - data.frame 中具有多个值的列

r - 在 dplyr 中使用变量列名汇总

r - data.table中POSIXct的高效对比

python - 我可以使用 ElementTree 获取 XML 文件的完整结构吗?

r - XGBoost 上的 AUC 指标

python - 从数据、周期范围和聚合函数创建 Pandas TimeSeries