最近,即將要實習的公司經理給了一個關於Prophet預測模型的案例,讓我去學習一下怎麼調參數。正好我早就想體驗一下傳說中「會一手調參數,就能夠在碩士圈混」的感覺了,🤣🤣🤣。本文主要經過簡單介紹Prophet模型及其重要參數,再結合京東訂單量的例子,加深對Prophet模型的瞭解。html
Prophet模型,英文直譯爲「先知」模型,是Facebook公司於2017開源的一個基於Python和R語言的時間序列預測算法。它適用於具備趨勢性、多種週期性(每一年每個月每週每日每小時等)、節假日效應,以及部分異常值的時間序列,該模型不須要使用者掌握深厚的時間序列分析的統計學知識,Facebook 表示,默認配置的Prophet就能夠生成媲美經驗豐富的專業數據分析師的預測,即便不是時序分析專家,也能夠理解該模型的重要參數。python
Prophet模型本質上是一個可加性迴歸模型,其基本形式以下:git
其中:github
下面分別爲Prophet模型(Python)中三大模型相關的主要參數,如下全部參數=
等號後面的值均爲默認值,對歷史數據進行擬合和預測時能夠根據具體的業務狀況對這些參數進行調整。算法
growth='linear'
Prophet模型默認使用分段線性模型,若是使用飽和增加模型(growth='logistic'
),必須給出飽和最大值cap
,飽和最小值floor
默認爲0changepoint_prior_scale=0.05
趨勢模型擬合的靈活度,值越大,靈活度越高 changepoint_range=0.8
表示突變點(即斜率突變的點)所在的範圍,如全部的突變點是基於前80%的歷史數據的n_changepoints=25
表示突變點的個數,如在前80%的歷史數據中,經過等分方法找到25個變點changepoints=None
手動設置突變點的位置,如changepoints=['2014-01-01']
interval_width=0.80
設置不肯定性區間的寬度seasonality_prior_scale=10.0
週期性模型擬合的靈活度,值越大,靈活度越高yearly_seasonality='auto'
表示週期性年份的傅立葉級數,當變化頻率很高時,能夠增大傅立葉級數weekly_seasonality='auto'
表示週期性周份指定傅立葉級數daily_seasonality='auto'
表示週期性日期的傅立葉級數 period
表示須要預測的點數fourier_order
表示傅立葉項數prior_scale
表示個別週期影響的程度 seasonality_mode='additive'
表示週期性模型使用的擬合模型,默認使用加法模型,可經過設置seasonality_mode='multiplicative'
設置爲乘法模型holidays_prior_scale=10.0
表示節假日模型擬合的靈活度,值越大,靈活度越高lower_window=0
/ upper_window=1
表示節假日影響的先後天數,注意:lower_window取值範圍爲0或負整數prior_scale
表示個別節假日影響的程度如今有京東2015.1.1——2018.3.13的訂單量數據,以下圖,用Prophet模型對此數據集進行擬合,而且預測將來一年的訂單量。api
....工具
拿到一個數據集時,首先對其進行數據清洗,剔除掉數據的異常值,提升數據的質量,這樣才更有利於數據的分析。數據處理以後,大體觀察此數據集,能夠對此數據集作簡單的圖表分析,以下圖爲這三年京東的訂單量的趨勢變化。學習
經過此折線圖能夠觀察到,每一年都有四個時期,訂單量出現的巨大的波動(三個波峯一個波谷)。接着,再仔細觀察某一年中這四個具體的時段,以下圖所示,網站
得知,這四個時期分別對應着春節、京東618購物節、雙11、雙十二,從而能夠在擬合和預測時,增長節假日模型的成分。
以下圖爲直接利用python進行擬合做圖的結果(源碼在最後附錄):
能夠看出,擬合的效果總體上仍是挺不錯的嘛 😄
若是想查看預測的各成分分析,可使用 Prophet.plot_components 方法。默認狀況下,將展現趨勢、時間序列的年度季節性和周季節性,若是包含了節假日,也會展現出來,以下圖所示:
ui
Prophet模型的算法在python中不是prophet,而是叫fbprophet,它在python的安裝方法,在Github上的介紹已經很詳細了:
https://github.com/facebook/p...
本文案例的python源碼
import pandas as pd from fbprophet import Prophet import matplotlib.pyplot as plt %matplotlib inline # 節假日數據 # 由於春節法定節日有一個星期,因此將春節的先後假日擴大至7天 # Spring Festival # 春節 TF_Spring=pd.DataFrame({ 'holiday':'Spring Festival', 'ds':pd.to_datetime(['2015-2-19','2016-2-8','2017-1-28','2018-2-16','2019-2-5']), 'lower_window': -3, 'upper_window': 4, }) # E-commerce festival 618 ECF_618 = pd.DataFrame({ 'holiday': 'ECF_618', 'ds': pd.to_datetime(['2015-6-18','2016-6-18','2017-6-18','2018-6-18']), 'lower_window': 0, 'upper_window': 1, }) # E-commerce festival 1111 ECF_1111 = pd.DataFrame({ 'holiday': 'ECF_1111', 'ds': pd.to_datetime(['2015-11-11','2016-11-11','2017-11-11','2018-11-11']), 'lower_window': 0, 'upper_window': 1, }) # E-commerce festival 1212 ECF_1212 = pd.DataFrame({ 'holiday': 'ECF_1212', 'ds': pd.to_datetime(['2015-12-12','2016-12-12','2017-12-12','2018-12-12']), 'lower_window': 0, 'upper_window': 1, }) # 合併全部節假日,做爲Prophet的形參 holidays=pd.concat((TF_Spring,ECF_618,ECF_1111,ECF_1212)) # 導入數據集,用pandas庫來讀取excel數據 df=pd.read_excel('./data.xlsx') # 轉換訂單量的數據類型 df['y']=df['y'].astype(float) # 初始化模型,設定Prophet模型的參數 m=Prophet(holidays=holidays,holidays_prior_scale=10.0,changepoint_prior_scale=0.15,daily_seasonality=True) # 進行擬合 m.fit(df) # 構建待預測的日期數據,periods=365表示從歷史數據的最後一天再日後推365天 future=m.make_future_dataframe(periods=365) future.tail() # 預測結果 forecast=m.predict(future) # 繪製預測結果 m.plot(forecast) # 預測的成分分析繪圖,展現時間序列的份量 m.plot_components(forecast); x1=forecast['ds'] y1=forecast['yhat'] plt.plot(x1,y1) plt.show()