library(fpp3)
library(readxl)
library(cowplot)
Milky_boy <- read_excel("~/Downloads/Milky boy.xlsx",
col_types = c("date", "numeric", "text"))
milk <- Milky_boy %>%
mutate(Month = yearmonth(Year)) %>%
select(Month, Price) %>%
as_tsibble(index = Month)
mplot <- autoplot(milk) +
labs(y = "Price in $", x = "Months", title = "Monthly Gallon Of Milk Prices")
## Plot variable not specified, automatically selected `.vars = Price`
mplot
milk %>%
model(STL(Price ~ season(window = 13), robust = TRUE)) %>%
components() %>%
autoplot() +
labs(title = "STL Decomp")
milk %>%
features(Price, unitroot_kpss)
## # A tibble: 1 × 2
## kpss_stat kpss_pvalue
## <dbl> <dbl>
## 1 1.29 0.01
milk %>%
features(Price, unitroot_ndiffs)
## # A tibble: 1 × 1
## ndiffs
## <int>
## 1 1
milk %>%
gg_tsdisplay(Price, plot_type = 'partial')
Milkdiff2 <- milk %>%
mutate(Price = difference(Price)) %>%
na.omit()
Milkdiff2 %>%
ggplot(aes(x = Month, y = Price)) +
geom_line(aes(y = Price))
Milkdiff2 %>%
features(Price, unitroot_kpss)
## # A tibble: 1 × 2
## kpss_stat kpss_pvalue
## <dbl> <dbl>
## 1 0.0914 0.1
Milkdiff2 %>%
features(Price, unitroot_ndiffs)
## # A tibble: 1 × 1
## ndiffs
## <int>
## 1 0
Milkdiff2 %>%
gg_tsdisplay(Price, plot_type = 'partial')
Milkauto <- milk %>%
model('Auto' = ARIMA(Price))
report(Milkauto)
## Series: Price
## Model: ARIMA(0,1,2)
##
## Coefficients:
## ma1 ma2
## 0.3441 0.1289
## s.e. 0.0613 0.0714
##
## sigma^2 estimated as 0.004806: log likelihood=342.2
## AIC=-678.41 AICc=-678.32 BIC=-667.58
Milkcomp <- milk %>%
model(
'012' = ARIMA(Price ~ pdq(0,1,2)),
'212' = ARIMA(Price ~ pdq(2,1,2)),
'110' = ARIMA(Price ~ pdq(1,1,0)),
"011" = ARIMA(Price ~ pdq(0,1,1)),
"111" = ARIMA(Price ~ pdq(1,1,1)))
Milkcomp %>%
glance()
## # A tibble: 5 × 8
## .model sigma2 log_lik AIC AICc BIC ar_roots ma_roots
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <list> <list>
## 1 012 0.00481 342. -678. -678. -668. <cpl [0]> <cpl [2]>
## 2 212 0.00474 345. -680. -680. -662. <cpl [2]> <cpl [2]>
## 3 110 0.00483 341. -678. -678. -671. <cpl [1]> <cpl [0]>
## 4 011 0.00485 341. -677. -677. -670. <cpl [0]> <cpl [1]>
## 5 111 0.00483 341. -677. -677. -666. <cpl [1]> <cpl [1]>
#012 and 212
MilkETSauto <- milk %>%
model('Auto' = ETS(Price))
report(MilkETSauto)
## Series: Price
## Model: ETS(M,N,N)
## Smoothing parameters:
## alpha = 0.9999
##
## Initial states:
## l[0]
## 2.783582
##
## sigma^2: 5e-04
##
## AIC AICc BIC
## 107.6908 107.7796 118.5301
MilkETS <- milk %>%
model(
'Auto' = ETS(Price),
'Simple' = ETS(Price ~ error("A") + trend("N") + season("N")),
'Holt' = ETS(Price ~ error("A") + trend("A") + season("N")),
'Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N")))
MilkETS %>%
glance()
## # A tibble: 4 × 9
## .model sigma2 log_lik AIC AICc BIC MSE AMSE MAE
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 Auto 0.000508 -50.8 108. 108. 119. 0.00532 0.0143 0.0150
## 2 Simple 0.00536 -51.7 109. 110. 120. 0.00532 0.0143 0.0493
## 3 Holt 0.00542 -52.3 115. 115. 133. 0.00535 0.0142 0.0494
## 4 Multiplicative Trend 0.00539 -51.4 113. 113. 131. 0.00531 0.0142 0.0493
#Auto
choochoo <- milk %>%
filter(year(Month) <= 2015)
choochoo
## # A tsibble: 192 x 2 [1M]
## Month Price
## <mth> <dbl>
## 1 2000 Jan 2.78
## 2 2000 Feb 2.78
## 3 2000 Mar 2.75
## 4 2000 Apr 2.77
## 5 2000 May 2.78
## 6 2000 Jun 2.76
## 7 2000 Jul 2.78
## 8 2000 Aug 2.81
## 9 2000 Sep 2.81
## 10 2000 Oct 2.80
## # … with 182 more rows
testies <- milk %>%
filter(year(Month) > 2015)
testies
## # A tsibble: 82 x 2 [1M]
## Month Price
## <mth> <dbl>
## 1 2016 Jan 3.31
## 2 2016 Feb 3.23
## 3 2016 Mar 3.19
## 4 2016 Apr 3.16
## 5 2016 May 3.16
## 6 2016 Jun 3.12
## 7 2016 Jul 3.06
## 8 2016 Aug 3.14
## 9 2016 Sep 3.23
## 10 2016 Oct 3.29
## # … with 72 more rows
Milkfour <- choochoo %>%
model(
'Mean' = MEAN(Price),
'Naive' = NAIVE(Price),
'Seasonal_naive' = SNAIVE(Price),
'Drift' = RW(Price ~ drift()))
Milkacc <- Milkfour %>%
forecast(h = 82)
accuracy(Milkacc, milk)
## # A tibble: 4 × 10
## .model .type ME RMSE MAE MPE MAPE MASE RMSSE ACF1
## <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 Drift Test -0.115 0.334 0.271 -4.44 8.32 1.03 0.953 0.945
## 2 Mean Test 0.0647 0.361 0.258 0.916 7.46 0.979 1.03 0.949
## 3 Naive Test -0.000817 0.355 0.270 -1.08 7.97 1.02 1.01 0.949
## 4 Seasonal_naive Test -0.112 0.393 0.326 -4.50 9.89 1.24 1.12 0.867
#Drift lowest RMSE
#Mean has lowest MAPE
Milktrain <- choochoo %>%
model(
'012' = ARIMA(Price ~ pdq(0,1,2)),
'212' = ARIMA(Price ~ pdq(2,1,2)),
'110' = ARIMA(Price ~ pdq(1,1,0)),
"011" = ARIMA(Price ~ pdq(0,1,1)),
"111" = ARIMA(Price ~ pdq(1,1,1)))
Milktrain %>%
glance()
## # A tibble: 5 × 8
## .model sigma2 log_lik AIC AICc BIC ar_roots ma_roots
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <list> <list>
## 1 012 0.00531 230. -454. -454. -445. <cpl [0]> <cpl [2]>
## 2 212 0.00515 234. -458. -457. -442. <cpl [2]> <cpl [2]>
## 3 110 0.00539 228. -452. -452. -446. <cpl [1]> <cpl [0]>
## 4 011 0.00545 227. -450. -450. -444. <cpl [0]> <cpl [1]>
## 5 111 0.00541 228. -451. -451. -441. <cpl [1]> <cpl [1]>
#012 and 212
best <- choochoo %>%
model(
'012' = ARIMA(Price ~ pdq(0,1,2)),
'212' = ARIMA(Price ~ pdq(2,1,2)),
'110' = ARIMA(Price ~ pdq(1,1,0)),
"011" = ARIMA(Price ~ pdq(0,1,1)),
"111" = ARIMA(Price ~ pdq(1,1,1))) %>%
forecast(h = 82)
accuracy(best, milk)
## # A tibble: 5 × 10
## .model .type ME RMSE MAE MPE MAPE MASE RMSSE ACF1
## <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 011 Test -0.00622 0.355 0.272 -1.25 8.02 1.03 1.01 0.949
## 2 012 Test -0.0143 0.355 0.274 -1.50 8.12 1.04 1.01 0.949
## 3 110 Test -0.00665 0.355 0.272 -1.26 8.03 1.03 1.01 0.949
## 4 111 Test -0.00789 0.355 0.272 -1.30 8.04 1.03 1.01 0.949
## 5 212 Test -0.00396 0.355 0.271 -1.18 8.00 1.03 1.01 0.949
#212 and 011 have lowest RMSE
#All RMSE are extremely close
#212 and 011 have lowest MAPE
#All are extremely close except 012
Milkband <- choochoo %>%
model(
'Auto' = ETS(Price),
'Simple' = ETS(Price ~ error("A") + trend("N") + season("N")),
'Holt' = ETS(Price ~ error("A") + trend("A") + season("N")),
'Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N")))
Milkband %>%
glance()
## # A tibble: 4 × 9
## .model sigma2 log_lik AIC AICc BIC MSE AMSE MAE
## <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 Auto 0.000573 -10.3 32.6 33.0 52.1 0.00582 0.0177 0.0156
## 2 Simple 0.00615 -14.9 35.8 35.9 45.6 0.00608 0.0168 0.0506
## 3 Holt 0.00648 -19.0 48.0 48.3 64.3 0.00635 0.0204 0.0537
## 4 Multiplicative Trend 0.00628 -15.9 41.8 42.1 58.1 0.00615 0.0168 0.0511
#Auto
MilkETS2 <- choochoo %>%
model(
'Auto' = ETS(Price),
'Simple' = ETS(Price ~ error("A") + trend("N") + season("N")),
'Holt' = ETS(Price ~ error("A") + trend("A") + season("N")),
'Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N"))) %>%
forecast(h = 82)
accuracy(MilkETS2, milk)
## # A tibble: 4 × 10
## .model .type ME RMSE MAE MPE MAPE MASE RMSSE ACF1
## <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 Auto Test 3.30e-2 0.357 0.263 -0.0530 7.66 0.996 1.02 0.949
## 2 Holt Test 8.20e-1 1.12 0.831 23.0 23.4 3.15 3.19 0.960
## 3 Multiplicative Tre… Test -6.83e-2 0.337 0.268 -3.07 8.09 1.01 0.962 0.947
## 4 Simple Test -8.16e-4 0.355 0.270 -1.08 7.97 1.02 1.01 0.949
#Multi has lowest RMSE
#Auto has lowest MAPE
Milkdrift <- choochoo %>%
model('Drift' = RW(Price ~ drift())) %>%
forecast(h = 82)
plot1 <- Milkdrift %>%
autoplot() +
autolayer(milk) +
labs(title = "Drift")
## Plot variable not specified, automatically selected `.vars = Price`
bestfr <- choochoo %>%
model('012' = ARIMA(Price ~ pdq(0,1,2))) %>%
forecast(h = 82)
plot2 <- bestfr %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (0,1,2)")
## Plot variable not specified, automatically selected `.vars = Price`
bestfr3 <- choochoo %>%
model('212' = ARIMA(Price ~ pdq(2,1,2))) %>%
forecast(h = 82)
plot3 <- bestfr3 %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (2,1,2)")
## Plot variable not specified, automatically selected `.vars = Price`
bestfr4 <- choochoo %>%
model('011' = ARIMA(Price ~ pdq(0,1,1))) %>%
forecast(h = 82)
plot4 <- bestfr4 %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (0,1,1)")
## Plot variable not specified, automatically selected `.vars = Price`
BestETS <- choochoo %>%
model('Auto' = ETS(Price)) %>%
forecast(h = 82)
plot5 <- BestETS %>%
autoplot() +
autolayer(milk) +
labs(title = "ETS Auto")
## Plot variable not specified, automatically selected `.vars = Price`
BestETS2 <- choochoo %>%
model('Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N"))) %>%
forecast(h = 82)
plot6 <- BestETS2 %>%
autoplot() +
autolayer(milk) +
labs(title = "ETS Multi")
## Plot variable not specified, automatically selected `.vars = Price`
plot_grid(plot1, plot2, plot3, plot4, plot5, plot6)
# Drift = 0.3337870 (Best) # ARIMA (012) = 0.3551251 (5th) # ARIMA (212) = 0.3548632 (3rd) # ARIMA (011) = 0.3548885 (4th) # ETS Auto = 0.3568725 (Last) # ETS Multi = 0.3358933 (2nd)
# Drift = 8.321966 (Last) # ARIMA (012) = 8.124391 (5th) # ARIMA (212) = 8.000688 (2nd) # ARIMA (011) = 8.024482 (3rd) # ETS Auto = 7.662227 (Best) # ETS Multi = 8.036521 (4th)
Milkdrift2 <- milk %>%
model('Drift' = RW(Price ~ drift()))
Milkdrift2 %>%
gg_tsresiduals() +
labs(title = "Drift resid")
## Warning: Removed 1 row(s) containing missing values (geom_path).
## Warning: Removed 1 rows containing missing values (geom_point).
## Warning: Removed 1 rows containing non-finite values (stat_bin).
augment(Milkdrift2) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 Drift 35.4 0.000108
AR012 <- milk %>%
model('012' = ARIMA(Price ~ pdq(0,1,2)))
AR012 %>%
gg_tsresiduals() +
labs(title = "ARIMA (0,1,2) resid")
augment(AR012) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 012 9.72 0.465
AR011 <- milk %>%
model('011' = ARIMA(Price ~ pdq(0,1,1)))
AR011 %>%
gg_tsresiduals() +
labs(title = "ARIMA (0,1,1) resid")
augment(AR011) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 011 10.9 0.369
AR212 <- milk %>%
model('212' = ARIMA(Price ~ pdq(2,1,2)))
AR212 %>%
gg_tsresiduals() +
labs(title = "ARIMA (2,1,2) resid")
augment(AR212) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 212 4.20 0.938
AutoETS <- milk %>%
model('Auto' = ETS(Price))
AutoETS %>%
gg_tsresiduals() +
labs(title = "ETS Auto")
augment(AutoETS) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 Auto 35.5 0.000101
MultiETS <- milk %>%
model('Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N")))
MultiETS %>%
gg_tsresiduals() +
labs(title = "ETS Multi")
augment(MultiETS) %>%
features(.resid, ljung_box, lag = 10, dof = 0)
## # A tibble: 1 × 3
## .model lb_stat lb_pvalue
## <chr> <dbl> <dbl>
## 1 Multiplicative Trend 35.7 0.0000939
# Drift = 0.0001077292 (Not WN) # ARIMA (012) = 0.4652559 (Is WN) #
ARIMA (212) = 0.9376757 (Is WN) # ARIMA (011) = 0.3686044 (Is WN) # ETS
Auto = 0.000101258 (Not WN)
# ETS Multi = 0.00009387677 (Not WN)
Milkdriftcast <- milk %>%
model('Drift' = RW(Price ~ drift())) %>%
forecast(h = 12)
plot11 <- Milkdriftcast %>%
autoplot() +
autolayer(milk) +
labs(title = "Drift")
## Plot variable not specified, automatically selected `.vars = Price`
bestfrcast <- milk %>%
model('012' = ARIMA(Price ~ pdq(0,1,2))) %>%
forecast(h = 12)
plot22 <- bestfrcast %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (0,1,2)")
## Plot variable not specified, automatically selected `.vars = Price`
bestfr3cast <- milk %>%
model('212' = ARIMA(Price ~ pdq(2,1,2))) %>%
forecast(h = 12)
plot33 <- bestfr3cast %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (2,1,2)")
## Plot variable not specified, automatically selected `.vars = Price`
bestfr4cast <- milk %>%
model('011' = ARIMA(Price ~ pdq(0,1,1))) %>%
forecast(h = 12)
plot44 <- bestfr4cast %>%
autoplot() +
autolayer(milk) +
labs(title = "ARIMA (0,1,1)")
## Plot variable not specified, automatically selected `.vars = Price`
BestETScast <- milk %>%
model('Auto' = ETS(Price)) %>%
forecast(h = 12)
plot55 <- BestETScast %>%
autoplot() +
autolayer(milk) +
labs(title = "ETS Auto")
## Plot variable not specified, automatically selected `.vars = Price`
BestETS2cast <- milk %>%
model('Multiplicative Trend' = ETS(Price ~ error("A") + trend("M") + season("N"))) %>%
forecast(h = 12)
plot66 <- BestETS2cast %>%
autoplot() +
autolayer(milk) +
labs(title = "ETS Multi")
## Plot variable not specified, automatically selected `.vars = Price`
plot_grid(plot11, plot22, plot33, plot44, plot55, plot66)
ModCompfr <- milk %>%
stretch_tsibble(.init = 10) %>%
model(
"Multiplicative Trend" = ETS(Price ~ error("A") + trend("M") + season("N")),
'Auto' = ETS(Price),
'212' = ARIMA(Price ~ pdq(2,1,2)),
'012' = ARIMA(Price ~ pdq(0,1,2)),
'011' = ARIMA(Price ~ pdq(0,1,1)),
'Drift' = RW(Price ~ drift())) %>%
forecast(h = 1)
## Warning: It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## Warning in sqrt(diag(best$var.coef)): NaNs produced
## Warning: It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## It looks like you're trying to fully specify your ARIMA model but have not said if a constant should be included.
## You can include a constant using `ARIMA(y~1)` to the formula or exclude it by adding `ARIMA(y~0)`.
## Warning: 11 errors (1 unique) encountered for 212
## [11] Could not find an appropriate ARIMA model.
## This is likely because automatic selection does not select models with characteristic roots that may be numerically unstable.
## For more details, refer to https://otexts.com/fpp3/arima-r.html#plotting-the-characteristic-roots
## Warning: 4 errors (1 unique) encountered for 012
## [4] Could not find an appropriate ARIMA model.
## This is likely because automatic selection does not select models with characteristic roots that may be numerically unstable.
## For more details, refer to https://otexts.com/fpp3/arima-r.html#plotting-the-characteristic-roots
accuracy(ModCompfr, milk)
## Warning: The future dataset is incomplete, incomplete out-of-sample data will be treated as missing.
## 1 observation is missing at 2022 Nov
## # A tibble: 6 × 10
## .model .type ME RMSE MAE MPE MAPE MASE RMSSE ACF1
## <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 011 Test 0.00448 0.0722 0.0512 0.115 1.55 0.195 0.215 0.0563
## 2 012 Test 0.00366 0.0729 0.0512 0.0935 1.55 0.196 0.217 0.0327
## 3 212 Test 0.00401 0.0681 0.0505 0.102 1.52 0.193 0.203 0.00678
## 4 Auto Test 0.00526 0.0745 0.0510 0.138 1.55 0.195 0.222 0.299
## 5 Drift Test 0.00145 0.0746 0.0508 0.0169 1.53 0.194 0.222 0.313
## 6 Multiplicative T… Test 0.00109 0.0770 0.0530 0.0118 1.61 0.203 0.229 0.320