Loading...
墨滴

Robinx

2021/03/31  阅读:45  主题:草原绿

时序预测工具fbprophet

fbprophet是facebook开源的一套工业级别的时序预测库,能够自动监测出数据集中的异常噪声,并以数据波动趋势项,季节项,节假日项作为特征进行拟合,适合于金融领域的数据预测,本文总结了该工具的使用,并在文末提供了该库的源码,论文,需要的朋友可自取

在发现这个库之前,小编也尝试过直接用线性最小二乘,GM,AR,LSTM等实现预测,但是他们都存在的一个问题就是,需要手工在模型中添加异常检测逻辑以控制噪声点的影响,否则,预测的效果还不如人工方法来的准,因为在工业使用上,数据往往是很脏的,往往预测这个玄学行为会由专门的市场分析人员和模型结果综合进行比对,而经过实验,发现最小二乘与灰度模型,只对于数据波动平稳的趋势尚好,但对于LSTM网络,输入的参数很难控制,很容易导致overfitting,于是小编在网上发现了这个库,虽然部署过程太特么难了,但是真正用起来才发现这个库对数据分析小白来说多么友好

来看网上的一张图

黑色点就是不同时刻的时序数据,蓝色区域代表着所有数据的波动趋势,可以看出,这个库比较适用于周期性较强的序列

在论文中,作者有讲述到,整个序列其实是由多个特征序列拟合,然后累加生成的,分别是季节项St,趋势项Tt,节假日项Ht,剩余项e

在趋势项中,作者使提供了logistic和分段linerregression两种方式去进行回归,在源码forecaster.py下面提供了关键的步骤

同时对于周期性特征,该模型用了傅立叶级数去模拟这段过程,可以通过调节输入参数seasonality_mode来控制季节性的影响权重

模型最后还引入了节假日项,论文中给出了几个节假日例子,同时还支持扩展,节假日也是由一个参数指标进行控制的,参数值越大,影响也越大

之前我们介绍过,prophet需要预测的是一类数据,他们有以下共同的特点

  • 观察值是按每小时或每天或每周或每月给出的一段历史数据
  • 引入了假期,法定节假日的影响
  • 数据中存在异常值或者缺失值
  • 历史趋势呈现周期性变化

我们将在后续的文章中对这个算法的原理进行分析,今天主要介绍下如何去使用

Prophet提供了许多输入参数

  • growth: 字符串‘linear’或‘logistic’,表示线性或者逻辑增长趋势。
  • changepoints: 日期型向量,指定潜在拐点,如果不指定,将会自动选择潜在拐点。例如:changepoints=[‘2014-01-01’]指定2014-01-01这一天是潜在的changepoints。
  • n_changepoints: 表示changepoints的数量大小,如果changepoints指定,该传入参数将不会被使用。如果 changepoints不指定,将会从输入的历史数据前80%中选取25个(个数由n_changepoints传入参数决定)潜在改变点。
  • changepoint_range: 估计趋势变化点的历史比例。如果指定了 changepoints,则不使用。
  • yearly_seasonality: 指定是否分析数据的年季节性,如果为True,默认取傅里叶项为10,最后会输出,yearly_trend,yearly_upper,yearly_lower等数据。
  • weekly_seasonality: 指定是否分析数据的周季节性,如果为True,默认取傅里叶项为10,最后会输出,weekly_trend,weekly_upper,weekly_lower等数据。
  • daily_seasonality: 指定是否分析数据的天季节性,如果为True,默认取傅里叶项为10,最后会输出,daily_trend, daily_upper, daily_lower等数据。
  • holidays: 传入dataframe 格式的数据。这个数据包含有holiday列 (string)和ds(date类型)和可选列lower_window和upper_window来指定该日期的lower_window或者upper_window范围内都被列为假期。lower_window=-2将包括前2天的日期作为假期。(默认None)
  • seasonality_mode: ‘additive’ (default) or ‘multiplicative’。季节模型。
  • seasonality_prior_scale: 调节季节性组件的强度。值越大,模型将适应更强的季节性波动,值越小,越抑制季节性波动。
  • holidays_prior_scale: 调节节假日模型组件的强度。值越大,该节假日对模型的影响越大,值越小,节假日的影响越小。
  • changepoint_prior_scale: 增长趋势模型的灵活度。调节“changepoint”选择的灵活度,值越大选择的“changepoint”越多,使模型对历史数据的拟合程度变强,然而也增加了过拟合的风险。
  • mcmc_samples: mcmc采样,用于获得预测未来的不确定性。若大于0,将做mcmc样本的全贝叶斯推理,如果为0,将做最大后验估计。
  • interval_width: 衡量未来时间内趋势改变的程度。表示预测未来时使用的趋势间隔出现的频率和幅度与历史数据的相似度,值越大越相似。当mcmc_samples = 0时,该参数仅用于增长趋势模型的改变程度,当mcmc_samples > 0时,该参数也包括了季节性趋势改变的程度。
  • uncertainty_samples: 用于估计不确定性区间的模拟抽取数

我们看一下如何去使用这个模型,在源码包下有一个很简单的测试集

ds代表着输入的时间序列,其必须支持YYYY-MM-DD这种格式,y代表序列值,可以看出这是个按日为步长进行预测的序列

import pandas as pd
import numpy as np
from fbprophet import Prophet
import matplotlib.pyplot as plt

# 数据文件请从github上的Prophet项目下载,并放在代码的对应目录
df = pd.read_csv('data.csv')
df['y'] = np.log(df['y'])
print (df.tail())

# 定义模型
m = Prophet()

# 训练模型
m.fit(df)

# 构建预测集,预测未来一年的涨势
future = m.make_future_dataframe(periods=365)
print (future.tail())

# 进行预测
forecast = m.predict(future)

print (forecast.tail(10))
forecast[['ds''yhat''yhat_lower''yhat_upper']].tail(10)
m.plot(forecast)
plt.show()

对结果进行分析,可以看出yhat_lower与yhat_upper分别界定了预测范围的下界和上界,该模型很好的适用于周期性数据的预测

如果要使这个模型工业化,仍然有还有很大提升的地方,首先是参数的调整,模型的参数很多,面对节假日与季节性明显的数据可以根据需要临时调整,其次是速度的提升,源码中并没看到是否用了多核,但拟合过程其实是基于pyStan库(底层C++)完成的,所以暂时能想到可以在文件读取和模型拟合这两个阶段尽量开多进程去跑,减少线上预测所消耗的总时间,,当然前提是cpu得够,同时用更高效的文件读取方式代替pandas,毕竟pandas虽然好用但是速度实在太慢了

今天大概能想的就这么多,脑回路已不够,喜欢的朋友点个赞在走呗~

论文地址

https://peerj.com/preprints/3190.pdf http://it.taocms.org/12/15346.htm

参考链接

https://www.jiqizhixin.com/articles/2019-02-19-11

源码地址

链接: https://pan.baidu.com/s/12lJCpGC7dR5qUcA1V4oPFg 密码: l74d

Robinx

2021/03/31  阅读:45  主题:草原绿

作者介绍

Robinx