Rでデータ解析を始めよう010 Rではじめての時系列分析(AirPassengers)

Rでデータ解析を始めよう010 Rではじめての時系列分析(AirPassengers)

モモノキ&ナノネと一緒に統計ソフトRの使い方を学習していきます。

モモノキ&ナノネと一緒にRで時系列分析を試してみよう




Rで時系列分析、AirPassengersデータとSARIMAモデルを使って予測をやってみよう

ナノネ、統計解析用フリーソフト『R』の使い方を練習するよ。今回は時系列分析をやってみよう。

時系列分析だね!データはPythonでも使ったAirPassenger?

うん。Rだとデフォルトでデータが入ってるから読み込みもラクチンだね。

さっそくAirPassengersのデータをチェックしてみよう。

In [87]:
AirPassengers
     Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec
1949 112 118 132 129 121 135 148 148 136 119 104 118
1950 115 126 141 135 125 149 170 170 158 133 114 140
1951 145 150 178 163 172 178 199 199 184 162 146 166
1952 171 180 193 181 183 218 230 242 209 191 172 194
1953 196 196 236 235 229 243 264 272 237 211 180 201
1954 204 188 235 227 234 264 302 293 259 229 203 229
1955 242 233 267 269 270 315 364 347 312 274 237 278
1956 284 277 317 313 318 374 413 405 355 306 271 306
1957 315 301 356 348 355 422 465 467 404 347 305 336
1958 340 318 362 348 363 435 491 505 404 359 310 337
1959 360 342 406 396 420 472 548 559 463 407 362 405
1960 417 391 419 461 472 535 622 606 508 461 390 432

飛行機乗客数のデータで1949年から1960年までの月次データ。数値は人数で、たしか千人単位だったよね。

In [88]:
plot(AirPassengers)

Rにおまかせでグラフにプロットしてみた。

In [89]:
class(AirPassengers)
'ts'

時系列データは『ts』とうい形式になるみたいだよ。

In [90]:
str(AirPassengers)
 Time-Series [1:144] from 1949 to 1961: 112 118 132 129 121 135 148 148 136 119 ...

tsはTime-Seriesの略みたいだね。

Rで時系列分析をやるのは今回が初めてだから、まだやりかたが良くわからないけど...。グーグル先生に質問しながら、とりあえず実践してみよう。

ラジャー。

まずはデータ準備。AirPassengersは144カ月、12年分のデータがあるね。モデルで予測もやりたいから、モデル作成用のデータは最後の1年分を除外しておこう。

In [91]:
data <- AirPassengers[1:132] # 1:(144-12)

最後の1年分を除外して、こんな感じかな??

In [92]:
print(data)
class(data)
  [1] 112 118 132 129 121 135 148 148 136 119 104 118 115 126 141 135 125 149
 [19] 170 170 158 133 114 140 145 150 178 163 172 178 199 199 184 162 146 166
 [37] 171 180 193 181 183 218 230 242 209 191 172 194 196 196 236 235 229 243
 [55] 264 272 237 211 180 201 204 188 235 227 234 264 302 293 259 229 203 229
 [73] 242 233 267 269 270 315 364 347 312 274 237 278 284 277 317 313 318 374
 [91] 413 405 355 306 271 306 315 301 356 348 355 422 465 467 404 347 305 336
[109] 340 318 362 348 363 435 491 505 404 359 310 337 360 342 406 396 420 472
[127] 548 559 463 407 362 405
'numeric'

モモノキ、ダメみたい。ts形式だったのに、ただのベクトルデータになっちゃった。

時系列データはts()を使ってデータを加工するといいみたい。

In [93]:
data <- ts(AirPassengers[1:132])
data
Time Series:
Start = 1 
End = 132 
Frequency = 1 
  [1] 112 118 132 129 121 135 148 148 136 119 104 118 115 126 141 135 125 149
 [19] 170 170 158 133 114 140 145 150 178 163 172 178 199 199 184 162 146 166
 [37] 171 180 193 181 183 218 230 242 209 191 172 194 196 196 236 235 229 243
 [55] 264 272 237 211 180 201 204 188 235 227 234 264 302 293 259 229 203 229
 [73] 242 233 267 269 270 315 364 347 312 274 237 278 284 277 317 313 318 374
 [91] 413 405 355 306 271 306 315 301 356 348 355 422 465 467 404 347 305 336
[109] 340 318 362 348 363 435 491 505 404 359 310 337 360 342 406 396 420 472
[127] 548 559 463 407 362 405

OK、ts形式に戻った。でも年月の設定が消えちゃったけど?

ts()のオプションで設定できるよ。startとfrequencyに値を渡せばいいみたい。今回の場合はstartにベクトルで開始の年と月、frequencyは月次データだから12を設定すればOK。

In [94]:
data <- ts(AirPassengers[1:132], start=c(1949, 1),frequency=12)
data
     Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec
1949 112 118 132 129 121 135 148 148 136 119 104 118
1950 115 126 141 135 125 149 170 170 158 133 114 140
1951 145 150 178 163 172 178 199 199 184 162 146 166
1952 171 180 193 181 183 218 230 242 209 191 172 194
1953 196 196 236 235 229 243 264 272 237 211 180 201
1954 204 188 235 227 234 264 302 293 259 229 203 229
1955 242 233 267 269 270 315 364 347 312 274 237 278
1956 284 277 317 313 318 374 413 405 355 306 271 306
1957 315 301 356 348 355 422 465 467 404 347 305 336
1958 340 318 362 348 363 435 491 505 404 359 310 337
1959 360 342 406 396 420 472 548 559 463 407 362 405

うまくいったかも。

次はモデルの作成だけど、そのまえに準備。『forecast』というのを使うからlibrary()で読み込んでおいてね。

In [95]:
# install.packages("forecast") # 必要に応じてインストール
library(forecast)

forecast準備OK。

参考までにstl()を使うと季節変動、トレンド、残差にデータを分離できるよ。グラフにも簡単にプロットできて、上から順に生データ、季節変動、トレンド、残差だよ。データチェックに活用できるね。

In [96]:
data.stl <- stl(data,s.window="periodic")
plot(data.stl)

Pythonで出力したグラフと一緒だ。

さっそくモデルをつくるよ。Rでも(S)ARIMAモデルを使ってみよう。

今回もまたモデルの最適次数とか探すの?Pythonで試したときけっこう手間取ったよね。

auto.arima()を実行すれば推奨次数をRが全部を教えてくれるから簡単だよ。auto.arimaのパラメータはコメントを参考にしてね。

In [97]:
model.arima <- auto.arima(
    data,              # データ指定
    ic = "aic",        # 情報量基準の指定
    trace = T,         # トレース出力(結果一覧)
    stepwise=T,        # 計算時の次数パターン省略 
    approximation=F,   # 近似計算の適用
    seasonal=T         # 季節調整
)
 ARIMA(2,1,2)(1,1,1)[12]                    : Inf
 ARIMA(0,1,0)(0,1,0)[12]                    : 905.0652
 ARIMA(1,1,0)(1,1,0)[12]                    : 900.8231
 ARIMA(0,1,1)(0,1,1)[12]                    : 901.7211
 ARIMA(1,1,0)(0,1,0)[12]                    : 899.9021
 ARIMA(1,1,0)(0,1,1)[12]                    : 901.0524
 ARIMA(1,1,0)(1,1,1)[12]                    : Inf
 ARIMA(2,1,0)(0,1,0)[12]                    : 901.3376
 ARIMA(1,1,1)(0,1,0)[12]                    : 900.9716
 ARIMA(2,1,1)(0,1,0)[12]                    : 902.9668

 Best model: ARIMA(1,1,0)(0,1,0)[12]                    

ARIMA(1,1,0)(0,1,0)[12]がベストだって言ってる。名前はARIMAだけど季節調整(SARIMA)にも対応してるんだ。

うん、季節調整の次数チェックもしてくれるから便利だね。もし手動でパレメータを設定したい場合は、下みたいなコードでモデルをつくれるよ。

In [98]:
arima(
    data,
    order=c(1,1,0),
    seasonal=list(order=c(0,1,0))
)
Call:
arima(x = data, order = c(1, 1, 0), seasonal = list(order = c(0, 1, 0)))

Coefficients:
          ar1
      -0.2431
s.e.   0.0894

sigma^2 estimated as 108.9:  log likelihood = -447.95,  aic = 899.9

tsdiag()で作成したモデルの残差などをグラフ化できるよ。

In [99]:
tsdiag(model.arima)

グラフが3個あるけど、見かたは?

一番上が残差プロット、2番目が残差の自己相関、3番目がリュング・ボックス検定だよ。

残差と残差の自己相関は小さいほどいいよ。検定はホワイトノイズか?のチェック的なもので、白点が青破線を下回らなければとりあえずOKだよ。

次は作成した(S)ARIMAモデルで予測をやってみよう。forecast()で予測を実行できるよ。引数はモデルとlevelに信頼区間、hに予測期数を指定すればOK。

In [100]:
pred = forecast(model.arima, level=95, h=12)
pred
class(pred)
         Point Forecast    Lo 95    Hi 95
Jan 1960       424.1099 403.5724 444.6474
Feb 1960       407.0557 381.2989 432.8125
Mar 1960       470.8257 440.0971 501.5544
Apr 1960       460.8817 426.0208 495.7426
May 1960       484.8681 446.2846 523.4515
Jun 1960       536.8714 494.9011 578.8417
Jul 1960       612.8706 567.7655 657.9757
Aug 1960       623.8708 575.8354 671.9062
Sep 1960       527.8707 477.0737 578.6677
Oct 1960       471.8707 418.4547 525.2868
Nov 1960       426.8707 370.9582 482.7832
Dec 1960       469.8707 411.5685 528.1729
'forecast'

そのままグラフにプロットもできるよ。

In [101]:
plot(pred)

Rだと信頼区間も簡単にプロットできて便利だね。

後半期間をグラフで拡大、予測期間もあと1年増やして2年分でやってみよう。

In [102]:
plot(
    forecast(model.arima, level = c(95), h = 24),
    flty = 2,
    xlim = c(1958, 1962),
    xaxp = c(1958, 1962, 4),
    ylim = c(200, 800),
    yaxp = c(200, 800, 3),
)

lines(AirPassengers, lwd=2)

legend("topleft",
    legend = c("pred", "actual"),
    lty = c(2, 1),
    lwd = 2,
    col = c(4, 1),
    cex = 1.5,
    bty = 'n',
    inset = c(0.05, 0.03)
)

けっこういい感じ?に予測できたかも。

今回のRで時系列分析は以上で。
またね!





スポンサーリンク

0 件のコメント :

コメントを投稿