引言

在以前的教程中,我们展示了如何可视化和操作时间序列数据,以及如何利用 ARIMA 方法从时间序列数据中产生预测。 我们注意到 ARIMA 模型的正确参数化可能是一个复杂的手工过程,需要一定的时间。

其他统计编程语言(比如 r)提供了自动化的方法来解决这个问题,但是这些语言还没有正式移植到 Python。 幸运的是,Facebook 的核心数据科学团队最近发布了一个名为 Prophet 的新方法,它可以让数据分析师和开发人员在 Python 3中进行大规模的预测。

先决条件

本指南将介绍如何在本地桌面或远程服务器上进行时间序列分析。 处理大型数据集可能需要大量内存,因此无论哪种情况,计算机都需要至少2 GB 的内存来执行本指南中的一些计算。

在本教程中,我们将使用 Jupyter Notebook 处理数据。 如果你还没有,你应该按照我们的教程来安装和设置 Python 3的 Jupyter Notebook。

第1步ー取出数据集并安装软件包

为了建立使用 Prophet 进行时间序列预测的环境,让我们首先进入本地编程环境或基于服务器的编程环境:

  • cd environments
  • . my_env/bin/activate

从这里,让我们为我们的项目创建一个新的目录。 我们将称之为时间片,然后移动到目录中。 如果你把这个项目叫做不同的名字,一定要用你的名字来代替整个指南中的时间段:

  • mkdir timeseries
  • cd timeseries

我们将使用 Box 和 Jenkins (1976)航空公司乘客数据集,其中包含1949年至1960年间每月航空公司乘客人数的时间序列数据。 您可以使用 curl 命令和-o 标志将输出写入文件并下载 CSV:

curl -O https://assets.digitalocean.com/articles/eng_python/prophet/AirPassengers.csv

本教程将需要 pandas、 matplotlib、 numpy、 cython 和 fbprophet 库。 像大多数其他 Python 软件包一样,我们可以使用 pip 安装 pandas、 numpy、 cython 和 matplotlib 库:

pip install pandas matplotlib numpy cython

为了计算它的预测,fbprophet 库依赖于 STAN 编程语言,以数学家 Stanislaw Ulam 命名。 因此,在安装 fbprophet 之前,我们需要确保 STAN 的 pystan Python 包装已经安装:

pip install pystan

完成后,我们可以使用 pip 来安装 Prophet:

pip install fbprophet

现在我们都已经安装好了,我们可以开始使用已安装的包了。

第二步ー汇入软件包及载入资料

为了开始处理我们的数据,我们将启动 Jupyter Notebook:

  • jupyter notebook

要创建一个新的笔记本文件,从右上角的下拉菜单中选择 New python3:

这将打开一个笔记本,允许我们加载所需的库。

作为最佳实践,可以从导入笔记本顶部所需的库开始(注意用于引用 pandas、 matplotlib 和 statsmodels 的标准缩写) :

%matplotlib inline
import pandas as pd
from fbprophet import Prophet

import matplotlib.pyplot as plt
plt.style.use('fivethirtyeight')

注意我们如何为我们的情节定义了538 matplotlib 风格。

在本教程中的每个代码块之后,您应该键入 ALT + ENTER 来运行代码并移动到笔记本中的新代码块中。

让我们从阅读时间序列数据开始。 我们可以加载 CSV 文件并用以下命令打印前5行:

df = pd.read_csv('AirPassengers.csv')

df.head(5)

我们的 DataFrame 显然包含一个 Month 和 AirPassengers 列。 Prophet 库希望输入一个 DataFrame,其中一列包含时间信息,另一列包含我们希望预测的度量。 重要的是,time 列应该是 datetime 类型,所以让我们检查一下我们的列的类型:

df.dtypes
Output
Month object AirPassengers int64 dtype: object

因为 Month 列不是日期时间类型,我们需要转换它:

df['Month'] = pd.DatetimeIndex(df['Month'])
df.dtypes
Output
Month datetime64[ns] AirPassengers int64 dtype: object

现在,我们看到 Month 列的日期时间类型是正确的。

Prophet 还强加了输入列命名为 ds (时间列)和 y (度量列)的严格条件,因此让我们重命名我们的 DataFrame 中的列:

df = df.rename(columns={'Month': 'ds',
                        'AirPassengers': 'y'})

df.head(5)

将我们将要使用的数据可视化是一个很好的实践,所以让我们画出我们的时间序列:

ax = df.set_index('ds').plot(figsize=(12, 8))
ax.set_ylabel('Monthly Number of Airline Passengers')
ax.set_xlabel('Date')

plt.show()

现在我们的数据已经准备好了,我们可以使用 Prophet 图书馆对我们的时间序列进行预测。

第三步: 利用先知进行时间序列预测

在本节中,我们将描述如何使用 Prophet 库来预测我们的时间序列的未来值。 Prophet 的作者们抽象了许多时间序列预测固有的复杂性,使得分析师和开发人员能够更直观地处理时间序列数据。

首先,我们必须实例化一个新的 Prophet 对象。 Prophet 使我们能够指定许多参数。 例如,我们可以通过设置区间宽度参数来指定不确定区间的期望范围。

# set the uncertainty interval to 95% (the Prophet default is 80%)
my_model = Prophet(interval_width=0.95)

现在我们的 Prophet 模型已经初始化,我们可以使用我们的 DataFrame 作为输入来调用它的 fit 方法。 模特的试穿应该不超过几秒钟。

my_model.fit(df)

你应该得到类似这样的输出:

Output
<fbprophet.forecaster.Prophet at 0x110204080>

为了获得我们时间序列的预测,我们必须向 Prophet 提供一个新的 DataFrame,其中包含一个 ds 列,其中包含我们需要预测的日期。 方便的是,我们不必手动创建这个 DataFrame,因为 Prophet 提供了 make future DataFrame 帮助函数:

future_dates = my_model.make_future_dataframe(periods=36, freq='MS')
future_dates.tail()

在上面的代码块中,我们指示 Prophet 在未来生成36个日期表。

在使用 Prophet 时,考虑我们的时间序列的频率是很重要的。 因为我们使用的是月度数据,所以我们清楚地指定了期望的时间戳频率(在这种情况下,MS 是月初)。 因此,make future 数据库为我们生成了36个月的时间戳。 换句话说,我们期待着预测3年后我们的时间序列的未来值。

然后将未来数据的数据模型作为输入,用于我们拟合模型的预测方法。

forecast = my_model.predict(future_dates)
forecast[['ds', 'yhat', 'yhat_lower', 'yhat_upper']].tail()

Prophet 返回一个包含许多有趣列的大型 datatrame,但是我们将输出子集到与预测最相关的列中,它们是:

  • Ds: 预测值的日期戳
  • Yhat: 我们的度量的预测值(在 Statistics 中,yhat 是一个传统用于表示值 y 的预测值的符号)
  • 我们预测的下限
  • 我们预测的上限

预计上述输出值的变化是因为 Prophet 依靠马尔科夫蒙特卡洛预测方法来生成其预测。 Mcmc 是一个随机过程,所以每次的值都会略有不同。

Prophet 还提供了一个方便的函数来快速绘制我们的预测结果:

my_model.plot(forecast,
              uncertainty=True)

Prophet 绘制我们的时间序列的观测值(黑点)、预测值(蓝线)和我们预测的不确定区间(蓝色阴影区域)。

Prophet 的另一个特别突出的特点是它能够返回我们预测的组成部分。 这可以帮助揭示每日、每周和每年的时间序列模式对总体预测值的贡献:

my_model.plot_components(forecast)

上面的情节提供了有趣的见解。 第一个图表显示,每月航空公司乘客量随着时间的推移呈线性增长。 第二个图表强调了一个事实,即每周的旅客人数在周末和周六达到高峰,而第三个图表显示,最多的旅客出现在7月和8月的假日期间。

总结

在本教程中,我们描述了如何使用 Prophet 库在 Python 中执行时间序列预测。 我们一直使用开箱即用的参数,但 Prophet 使我们能够指定更多的参数。 特别是,Prophet 提供了将您自己对时间序列的知识放到表中的功能。

以下是一些你可以尝试的附加事项:

  • 评估假期的影响,包括你的先前知识的假期月(例如,我们知道,十二月是一个假期月)。 关于假日建模的官方文档将会很有帮助。
  • 改变你的不确定性时间间隔的范围,或者进一步预测未来。

为了获得更多的实践,您还可以尝试加载另一个时间序列数据集来生成您自己的预测。 总体而言,Prophet 提供了许多引人注目的特性,包括根据用户需求定制预测模型的机会。