Как вернуть адаптированные значения ARIMA для данных дифференцированного временного ряда 2-го порядка в исходную форму? - PullRequest
1 голос
/ 05 августа 2020

Я попытался подобрать модель ARIMA для временного ряда Набор данных (ссылка)

Однако мои подогнанные значения не совпадают с исходными данными, когда я строю два графика. Также мой RMSE показывает очень большое значение. Я выполнил все необходимые шаги, например, сделал временной ряд стационарным путем дифференцирования. Я даже проверил стационарность с помощью скользящей статистики и теста Дики Фуллера, которые оказались убедительными. Тем не менее, окончательные результаты не являются удовлетворительными. Скажите, пожалуйста, где я ошибся.

Мой код:

import pandas as pd
import seaborn as sb
import matplotlib.pyplot as plt
import numpy as np
import datetime as dt
%matplotlib inline
plt.style.use('seaborn-ticks')
plt.rcParams['figure.figsize'] = (10,4)

file = 'C:/Users/pavan m sunder/projects/datascience/datasets/inpatient_waitinglist.xlsx'
data = pd.read_excel(file, parse_dates=['Date'], index_col='Date')
ts=pd.Series(data.impatient_waiting_list.values, index=data.index, name='inpatient_waiting_list')
ts.index = pd.DatetimeIndex(ts.index.values, freq=ts.index.inferred_freq)
ts.head()

ts.plot(kind='line')
plt.title('Original time series')

def test_stationarity(timeseries):
    #Determing rolling statistics
    moving_avg = timeseries.rolling(window=12).mean()
    moving_std = timeseries.rolling(window=12).std()

    #Plot rolling statistics:
    fig, ax = plt.subplots(figsize = (10,4))
    sb.lineplot(data = timeseries, legend = False, label = 'Original')
    sb.lineplot(data = moving_avg, palette = ['red'], legend = False, label = 'Rollmean')
    sb.lineplot(data = moving_std, palette = ['black'], legend = False, label = 'Rollstd')
    plt.title('Rolling statistics to check stationarity')
    plt.legend(loc='best')
    plt.show()
    
    #Perform Dickey-Fuller test:
    from statsmodels.tsa.stattools import adfuller

    print('Results of Dickey-Fuller Test:')
    dftest = adfuller(timeseries, autolag='AIC')
    dfoutput = pd.Series(dftest[0:4], index=['Test Statistic','p-value','#Lags Used','Number of Observations Used'])
    for key,value in dftest[4].items():
        dfoutput['Critical Value (%s)'%key] = value
    print(dfoutput)
    print('Testing test statistic ({}) < 1% confidence interval ({})?: {}'.format(dftest[0], dftest[4]['1%'], (dftest[0] < dftest[4]['1%']) ))
    print('Testing test statistic ({}) < 5% confidence interval ({})?: {}'.format(dftest[0], dftest[4]['5%'], (dftest[0] < dftest[4]['5%']) ))
    print('Testing test statistic ({}) < 10% confidence interval ({})?: {}'.format(dftest[0], dftest[4]['10%'], (dftest[0] < dftest[4]['10%']) ))
    return dftest

ts_log = np.log(ts)
ts_diff = ts_log.diff()
ts_diff2 = ts_diff.diff()
ts_diff2.dropna(inplace=True)
stn = test_stationarity(ts_diff2)

from statsmodels.tsa.stattools import acf, pacf

lag_acf = acf(ts_diff2, nlags=20, fft=False)
lag_pacf = pacf(ts_diff2, nlags=20, method='ols')

#Plot PACF and ACF:
fig, ax = plt.subplots(nrows = 2, ncols = 1, figsize = (10,6))
fig.tight_layout(pad=4.0)

sb.lineplot(data = lag_pacf, ax = ax[0])
ax[0].set_xticks(range(1,len(lag_pacf)))
ax[0].set_xlabel('Lag')
ax[0].set_ylabel('Partial auto correlation')
ax[0].axhline(y=0,linestyle='--',color='gray')
ax[0].axhline(y=-1.96/np.sqrt(len(lag_pacf)),linestyle='--',color='gray')
ax[0].axhline(y=1.96/np.sqrt(len(lag_pacf)),linestyle='--',color='gray')
ax[0].set_title('Figure 4(a): Partial autocorrelation function')

sb.lineplot(data = lag_acf, ax = ax[1])
ax[1].set_xticks(range(1,len(lag_acf)))
ax[1].axhline(y=0,linestyle='--',color='gray')
ax[1].axhline(y=-1.96/np.sqrt(len(lag_acf)),linestyle='--',color='gray')
ax[1].axhline(y=1.96/np.sqrt(len(lag_acf)),linestyle='--',color='gray')
ax[1].set_title('Figure 4(b) : Auto correlation funtion')

# ARIMA MODEL
from statsmodels.tsa.arima_model import ARIMA
model = ARIMA(ts_log, order=(1, 2, 1))
results_ARIMA = model.fit(disp=-1)
plt.figure(figsize=(10,4))
plt.plot(ts_diff)
plt.plot(results_ARIMA.fittedvalues, color='red')
plt.title('RSS: %.4f'% sum((results_ARIMA.fittedvalues-ts_diff2)**2))

predictions_ARIMA_diff = pd.Series(results_ARIMA.fittedvalues, copy=True)
predictions_ARIMA_diff_cumsum = predictions_ARIMA_diff.cumsum()
predictions_ARIMA_logb = pd.Series(ts_diff[1], index=ts_diff.index[1:])
predictions_ARIMA_logb = predictions_ARIMA_logb.add(predictions_ARIMA_diff_cumsum, fill_value=0)

predictions_ARIMA_diff_cumsum = predictions_ARIMA_logb.cumsum()
predictions_ARIMA_log = pd.Series(ts_log[0], index=ts_log.index)
predictions_ARIMA_log = predictions_ARIMA_log.add(predictions_ARIMA_diff_cumsum, fill_value=0)

predictions_ARIMA = np.exp(predictions_ARIMA_log)
predictions_ARIMA.head()

plt.plot(ts)
plt.plot(predictions_ARIMA)
plt.title('RMSE: %.4f'% np.sqrt(sum((predictions_ARIMA-ts)**2)/len(ts)))
...