ARIMA模型 - [SPSS & Python]


  簡介:

  ARIMA模型:(英語:Autoregressive Integrated Moving Average model),差分整合移動平均自回歸模型,又稱整合移動平均自回歸模型(移動也可稱作滑動),是時間序列預測分析方法之一。AR是“自回歸”,p為自回歸項數;MA為“滑動平均”,q為滑動平均項數,d為使之成為平穩序列所做的差分次數(階數)。

  由於畢業論文要涉及到時間序列的數據(商品的銷量)進行建模與分析,主要是對時間序列的數據進行預測,在對數據進行簡單的散點圖觀察時,發現數據具有季節性,也就是說:數據波動呈現着周期性,並且前面的數據會對后面的數據產生影響,這也符合商品的銷量隨時間波動的影響。於是選擇了ARIMA模型,那為什么不選擇AR模型、MA模型、ARMA模型???

  於是,通過這篇博客,你將學到:

  (1)通過SPSS操作ARIMA模型

  (2)運用python進行白噪聲數據判斷

  (3)為什么差分,怎么定階

  PS:在博客結尾,會附錄上Python進行ARIMA模型求解的代碼。

  為什么會使用SPSS?

  由於真香定理,在SPSS里有ARIMA、AR、MA模型的各種操作;還包括異常值處理,差分,白噪聲數據判斷,以及定階。 一種很方便又不用編程還可以避免改代碼是不是很爽…

  ARIMA模型的步驟

  好啦,使用ARIMA模型的原因:

  在過去的數據對今天的數據具有一定的影響,如果過去的數據沒有對如今的數據有影響時,不適合運用ARIMA模型進行時間序列的預測。

  使用ARIMA進行建模的步驟:

  簡單來說,運用ARIMA模型進行建模時,主要的步驟可以分成以下三步:

  (1)獲取原始數據,進行數據預處理。(缺失值填補、異常值替換)

  (2)對預處理后的數據進行平穩性判斷。如果不是平穩的數據,則要對數據進行差分運算。

  (3)將平穩的數據進行白噪聲檢驗;如果不是白噪聲數據,則說明數據之間仍然有關聯,需要進行ARIMA(p,d,q)重新定階:p、q。

  (4)當最后檢驗的數據是白噪聲數據,模型結束。

  接下來,就是用SPSS與Python進行實操。

  1 原始數據預處理

  首先數據來源是:2019年華中賽數學建模B題的數據。通過對一部分數據進行篩選后得到了可以運用模型建立的數據。如下圖所示:

  當然我們在拿到新的數據后,需要對數據進行缺失值填補,以及異常值判斷。這里不再展示預處理的相關操作。下面有對應的操作鏈接:

  缺失值填補:https://jingyan.baidu.com/article/d8072ac456536bec95cefdb6.html

  異常值處理:https://wenku.baidu.com/view/bd0289ca6d85ec3a87c24028915f804d2b1687aa.html?fr=search

  2 平穩性檢驗

  在獲取了預處理后的數據后,我們就可以進行下一步平穩性檢驗;簡單來說,平穩性也就是時間序列的數據是不是在某一數據上下波動,轉化成數學術語就是:均值和反差不會隨着時間變化而變化。於是可以使用SPSS畫出數據的散點圖,然后通過散點圖的圖像顯示來判斷是否是平穩性數據,如果不是平穩的數據就需要進行差分。

  觀察圖像可以看出,原始數據是有很弱的季節性,但是數據是非平穩的。從2018年12月份,商品號SS73210銷量就明顯下降,而不是在某一確定值上下波動。於是,對數據使用一階差分。

  為什么差分? 處理非平穩的數據,消除其相關性使其變成平穩性數據。

  差分后的數據為:

  同時,在我們獲取了相應的平穩的數據后,要進行白噪聲檢驗。

  下面是獲取差分后的數據值,然后與運用Python進行運算。

  最終,獲取一階差分后的數據:SS73210_1

  3 白噪聲檢驗

  獲取了差分后的數據SS73210_1后,運用Python進行白噪聲檢驗,要進行白噪聲檢驗的目的:檢驗圍繞某一條線上下波動的時間序列數據是不是隨機上下波動的。

  (白噪聲數據:隨機數據,Sig>0.05,則是白噪聲序列,則歷史的數據不能對未來進行預測和推斷,及殘差的ACF在置信區間內,可以認為等於0,過去的數據影響到今日的數據的這部分數據,這份信息已經被這個模型給提取出來了。)

  接下來就是運用Python進行對序列的白噪聲判斷:

  '''

  1.實現一階差分的白噪聲數據的判斷

  '''

  import pandas as pd

  from statsmodels.stats.diagnostic import acorr_ljungbox as lb

  path = 'D:/Python/Python_learning/HBUT/預處理/ARIMA.xlsx'

  df1 = pd.read_excel(path)

  p_value = lb(df1, lags= 1)

  print('白噪聲檢驗p值:', p_value)

  檢驗結果:

  白噪聲檢驗p值: (array([28.53145736]), array([9.21884666e-08])

  結果分析:原假設為數據是白噪聲的數據,由於模型檢驗的p值為9.21884666e-08小於0.05,為小概率事件,認為原假設成立不是白噪聲數據。所以需要運用ARIMA模型進行重新定階。

  4 重新定階

  ARIMA模型的定階有兩個參數p,q,一般可以通過具體的自相關,偏相關圖的截尾來確定階數,這里使用SPSS的操作進行自己定階,然后通過顯著性sig參數來判斷模型定階后的參數是夠可靠。

  1:這里有SPSS自動的操作:“專家建模器”

  2 :也可以通過方法 “ARIMA模型” 進行自定義參數p,d,q的階數。

  我這里選擇的模型的參數p,d,q都為1,也就是進行一階差分,p(自回歸項數)與q(滑動平均項數)都為1。

  下面是使用了上面的模型后的模型結果:

  從圖像可以看出運用了ARIMA模型(1,1,1)后,顯著性為0.135是大於0.05,認為此模型的數據為白噪聲的數據,也就是說,過去的數據影響到今日的數據的這部分數據,這份信息已經被這個模型給提取出來了。

  再通過殘差ACF與殘差PACF也是用來看相關性,如果大部分的數據是處於兩條線之間的,說明之間的數據是弱相關,幾乎沒有什么相關性,影響程度的信息已經被提取了。

  PS:編寫Python,進行參數定階

  '''

  #相對最優模型(p,q)

  data_ = data_.astype(float) #銷量轉為float類型

  #定階

  pmax = int(len(D_data)/30) #一般階數不超過length/10

  qmax = int(len(D_data)/30) #一般階數不超過length/10

  bic_matrix = [] #bic矩陣

  for p in range(pmax+1):

  tmp = []

  for q in range(qmax+1):

  try: #存在部分報錯,所以用try來跳過報錯。

  tmp.append(ARIMA(data_, (p, 1, q)).fit().bic)

  except:

  tmp.append(None)

  bic_matrix.append(tmp)

  bic_matrix = pd.DataFrame(bic_matrix) #從中可以找出最小值

  p, q = bic_matrix.stack().idxmin() #先用stack展平,然后用idxmin找出最小值位置。

  print(u'BIC最小的p值和q值為:%s、%s' %(p, q))

  '''

  5 預測

  在選好了參數后,我們需要運用模型進行后來5天的銷量進行預測。

  這里運用Python進行預測:

  # 選取好p,q后進行ARIMA預測

  model = ARIMA(data_, (p,1,q) ).fit() # 建立ARIMA(1, 1, 1)模型

  model.summary2() # 給出一份模型報告

  r = model.forecast(5) # 做出未來五天的預測結果

  pro_r = r[0]

  預測結果:

  做出未來五天的預測結果:

  [ 9.49325086 9.25931922 10.35808756 8.96617407 9.23941594]

  我這里也加上了完整的ARIMA算法的Python的代碼:

  # -*- coding: utf-8 -*-

  # @Time : 2020/4/3 22:50

  '''

  1.運用模型:ARIMA

  '''

  import pandas as pd

  import numpy as np

  import matplotlib.pyplot as plt

  import seaborn as sns #seaborn畫出的圖更好看,且代碼更簡單,缺點是可塑性差

  from statsmodels.graphics.tsaplots import plot_acf #自相關圖

  from statsmodels.tsa.stattools import adfuller as ADF #平穩性檢測

  from statsmodels.graphics.tsaplots import plot_pacf #偏自相關圖

  from statsmodels.stats.diagnostic import acorr_ljungbox #白噪聲檢驗

  from statsmodels.tsa.arima_model import ARIMA #引入ARIMA模型

  #seaborn 是建立在matplotlib之上的

  #文件的導入,和data的選取。

  inputfile = 'D:/Python/Python_learning/HBUT/model_3/test_four.xlsx'

  data = pd.read_excel(inputfile ,sheet_name= 'Sheet2', index_col = '日期')

  print(data.head())

  print(data[-5:])鄭州好的婦科醫院 http://www.zzkedayy.com/

  data_1 = data['SS81346']; data_2 = data['SS81004']

  data_3 = data['SS73210']; data_4 = data['SS81516']; data_5 = data['SS81376']

  data_ = data_5

  #seaborn設置背景

  sns.set(color_codes=True)

  plt.rcParams['font.sans-serif'] = ['SimHei'] #用來正常顯示中文標簽

  plt.rcParams['axes.unicode_minus'] = False #用來正常顯示負號

  plt.rcParams['figure.figsize'] = (8, 5) #設置輸出圖片大小

  #自相關圖

  #自相關圖顯示自相關系數長期大於零,說明時間序列有很強的相關性

  f = plt.figure(facecolor='white')

  ax1 = f.add_subplot(1, 1, 1)

  data_drop = data_.dropna() #將數據data dropna()

  plot_acf(data_drop, lags=31, ax=ax1)

  #平穩性檢查

  print(u'原始序列的ADF檢驗結果為:')

  print(ADF(data_)) #通過導入的ADF模塊返回銷量的平穩性檢查

  #單位根統計量對應的p的值顯著大於0.05,最終判斷該序列是非平穩序列

  #1階差分后的時序圖

  f = plt.figure(facecolor='white')

  ax2 = f.add_subplot(1, 1, 1)

  D_data = data_.diff().dropna() #1階差分,丟棄na值

  D_data.plot(ax = ax2)

  print(u'一階差分序列的ADF檢驗結果為:')

  print(ADF(D_data))

  #輸出p值遠小於0.05,所以1階差分之后是平穩非白噪聲序列

  #繪制一階差分前后的圖像

  f = plt.figure(facecolor='white')

  ax3 = f.add_subplot(2, 1, 1)

  plot_acf(D_data, lags=31, ax=ax3) #自相關

  ax4 = f.add_subplot(2, 1, 2)

  plot_pacf(D_data, lags=31, ax=ax4) #偏相關

  p = 1

  q = 1

  #選取好p,q后進行ARIMA預測

  model = ARIMA(data_, (p,1,q) ).fit() #建立ARIMA(1, 1, 1)模型

  model.summary2() #給出一份模型報告

  r = model.forecast(5) #做出未來五天的預測結果

  pro_r = r[0]

  print('做出未來五天的預測結果:')

  print(pro_r)

  #添加預測值到圖像上

  pre_data = pd.Series(pro_r, index=['2019/03/13', '2019/03/14', '2019/03/15', '2019/03/16', '2019/03/17'], name='SS81346')

  pre_data.index.name = '日期'

  #繪圖

  fig = plt.figure()

  ax = fig.add_subplot(1, 1, 1)

  ax.plot(data_, 'k', label='one')

  ax.plot(pre_data,'r', label='two')

  ax.set_title('商品: SS81376')

  ax.set_xlabel('日期')

  ax.set_ylabel('銷量')

  ax.set_xticks(['2018/09/01', '2018/10/01', '2018/11/01',

  '2018/12/01', '2019/01/01', '2019/02/01', '2019/02/28', '2019/03/18'])

  plt.show()

  得出圖像

  從圖像可以看出,黑色部分的數據是原有的數據,紅色的數據為銷量預測的數據,可以看出預測的后5天的數據具有很好的效果,也能夠很好的反映模型的預測能力。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM