Il y a trois problèmes mineurs par tseries::armarapport à ceux stats::arimaqui conduisent à un résultat légèrement différent dans le modèle ARMA pour les séries différenciées utilisant tseries::armaet ARIMA dans stats::arima.
Valeurs de départ des coefficients: stats::arimamet les coefficients AR et MA initiaux à zéro, tandis que tseries::armala procédure décrite dans Hannan et Rissanen (1982) est utilisée pour obtenir les valeurs initiales des coefficients.
Echelle de la fonction objectif: la fonction objectif en tseries::armaretourne la valeur des sommes conditionnelles des carrés, RSS; stats::arimaretourne 0.5*log(RSS/(n-ncond)).
Algorithme d'optimisation: par défaut, Nelder-Mead est utilisé dans tseries::arma, tout en utilisant stats::arimal'algorithme BFGS.
Le dernier peut être modifié via l'argument optim.methoddans stats::arimamais les autres nécessiteraient de modifier le code. Ci-dessous, je montre une version abrégée du code source (code minimal pour ce modèle particulier) pour stats::arimalequel les trois problèmes mentionnés ci-dessus sont modifiés afin qu'ils soient les mêmes que dans tseries::arma. Après avoir résolu ces problèmes, le même résultat que dans tseries::armaest obtenu.
Version minimale de stats::arima(avec les changements mentionnés ci-dessus):
# objective function, conditional sum of squares
# adapted from "armaCSS" in stats::arima
armaCSS <- function(p, x, arma, ncond)
{
# this does nothing, except returning the vector of coefficients as a list
trarma <- .Call(stats:::C_ARIMA_transPars, p, arma, FALSE)
res <- .Call(stats:::C_ARIMA_CSS, x, arma, trarma[[1L]], trarma[[2L]], as.integer(ncond), FALSE)
# return the conditional sum of squares instead of 0.5*log(res),
# actually CSS is divided by n-ncond but does not relevant in this case
#0.5 * log(res)
res
}
# initial values of coefficients
# adapted from function "arma.init" within tseries::arma
arma.init <- function(dx, max.order, lag.ar=NULL, lag.ma=NULL)
{
n <- length(dx)
k <- round(1.1*log(n))
e <- as.vector(na.omit(drop(ar.ols(dx, order.max = k, aic = FALSE, demean = FALSE, intercept = FALSE)$resid)))
ee <- embed(e, max.order+1)
xx <- embed(dx[-(1:k)], max.order+1)
return(lm(xx[,1]~xx[,lag.ar+1]+ee[,lag.ma+1]-1)$coef)
}
# modified version of stats::arima
modified.arima <- function(x, order, seasonal, init)
{
n <- length(x)
arma <- as.integer(c(order[-2L], seasonal$order[-2L], seasonal$period, order[2L], seasonal$order[2L]))
narma <- sum(arma[1L:4L])
ncond <- order[2L] + seasonal$order[2L] * seasonal$period
ncond1 <- order[1L] + seasonal$period * seasonal$order[1L]
ncond <- as.integer(ncond + ncond1)
optim(init, armaCSS, method = "Nelder-Mead", hessian = TRUE, x=x, arma=arma, ncond=ncond)$par
}
Maintenant, comparez les deux procédures et vérifiez qu'elles donnent le même résultat (nécessite la série xgénérée par l'OP dans le corps de la question).
En utilisant les valeurs initiales choisies dans tseries::arima:
dx <- diff(x)
fit1 <- arma(dx, order=c(3,3), include.intercept=FALSE)
coef(fit1)
# ar1 ar2 ar3 ma1 ma2 ma3
# 0.33139827 0.80013071 -0.45177254 0.67331027 -0.14600320 -0.08931003
init <- arma.init(diff(x), 3, 1:3, 1:3)
fit2.coef <- modified.arima(x, order=c(3,1,3), seasonal=list(order=c(0,0,0), period=1), init=init)
fit2.coef
# xx[, lag.ar + 1]1 xx[, lag.ar + 1]2 xx[, lag.ar + 1]3 ee[, lag.ma + 1]1
# 0.33139827 0.80013071 -0.45177254 0.67331027
# ee[, lag.ma + 1]2 ee[, lag.ma + 1]3
# -0.14600320 -0.08931003
all.equal(coef(fit1), fit2.coef, check.attributes=FALSE)
# [1] TRUE
En utilisant les valeurs initiales choisies dans stats::arima(zéros):
fit3 <- arma(dx, order=c(3,3), include.intercept=FALSE, coef=rep(0,6))
coef(fit3)
# ar1 ar2 ar3 ma1 ma2 ma3
# 0.33176424 0.79999112 -0.45215742 0.67304072 -0.14592152 -0.08900624
init <- rep(0, 6)
fit4.coef <- modified.arima(x, order=c(3,1,3), seasonal=list(order=c(0,0,0), period=1), init=init)
fit4.coef
# [1] 0.33176424 0.79999112 -0.45215742 0.67304072 -0.14592152 -0.08900624
all.equal(coef(fit3), fit4.coef, check.attributes=FALSE)
# [1] TRUE
fit1n'a qu'un seul paramètre MA & 1 AR: vouliez-vous direfit1<-arma(diff(x,1,lag=1),c(3,3),include.intercept=F)?