1-Schritt-Voraus-Vorhersagen mit dem Dynlm R-Paket

11

Ich habe ein Modell mit mehreren unabhängigen Variablen, von denen eine die Verzögerung der abhängigen Variablen ist, mithilfe des Dynlm-Pakets angepasst.

Angenommen, ich habe 1-Schritt-Voraus-Prognosen für meine unabhängigen Variablen. Wie erhalte ich 1-Schritt-Voraus-Prognosen für meine abhängigen Variablen?

Hier ist ein Beispiel:

library(dynlm)

y<-arima.sim(model=list(ar=c(.9)),n=10) #Create AR(1) dependant variable
A<-rnorm(10) #Create independant variables
B<-rnorm(10)
C<-rnorm(10)
y<-y+.5*A+.2*B-.3*C #Add relationship to independant variables 
data=cbind(y,A,B,C)

#Fit linear model
model<-dynlm(y~A+B+C+L(y,1),data=data)

#Forecast
A<-c(A,rnorm(1)) #Assume we already have 1-step forecasts for A,B,C
B<-c(B,rnorm(1))
C<-c(C,rnorm(1))
y=window(y,end=end(y)+c(1,0),extend=TRUE)
newdata<-cbind(y,A,B,C)
predict(model,newdata)

Und hier ist ein Beispiel mit dem Dyn-Paket, das funktioniert.

library(dyn)

#Fit linear model
model<-dyn$lm(y~A+B+C+lag(y,-1),data=data)

#Forecast
predict(model,newdata)the dyn packages, which works:
Zach
quelle
Wenn Sie nur das dynlmPaket verwenden, werden keine Prognosen für Ihre abhängigen Variablen bereitgestellt. Für die Bereitstellung von Prognosen für Ihre abhängigen Variablen sind ein Modell zur Erläuterung und wahrscheinlich zusätzliche Daten erforderlich. Ich empfehle Ihnen, etwas über multivariate Regression zu lesen, wie "Applied Multivariate Statistical Analysis" von Johnson und Wichern. oder ein Kurs über Prognosen: duke.edu/~rnau/411home.htm
deps_stats
1
@deps_stats Die abhängige Variable ist das, was ich vorhersagen möchte. Ich gehe davon aus, dass ich bereits Prognosen für meine unabhängigen Variablen habe. In meinem Beispielcode ist y die abhängige Variable, die ich prognostizieren möchte, und A, B, C sind die unabhängigen Variablen, für die ich bereits Prognosen habe. Wenn Sie den von mir veröffentlichten Beispielcode ausführen, werden Sie die Art meines Problems verstehen.
Zach
@Zach: Schöne Kaggle Bewertung! (Ich habe durch den Link in Ihrem Mouse-Over-Profil geklickt)
Hugh Perkins

Antworten:

13

Herzlichen Glückwunsch, Sie haben einen Fehler gefunden. Die Vorhersage für dynlmmit neuen Daten wird unterbrochen, wenn verzögerte Variablen verwendet werden. Um zu sehen, warum schauen Sie sich die Ausgabe von an

predict(model)
predict(model,newdata=data)

Die Ergebnisse sollten gleich sein, sind es aber nicht. Ohne newdataArgument predicterfasst die Funktion grundsätzlich ein modelElement aus der dynlmAusgabe. Mit newdataArgument wird predictversucht, eine neue Modellmatrix aus zu bilden newdata. Da dies das Parsen der gelieferten Formel beinhaltet dynlmund die Formel eine Funktion hat L, die nur intern in der Funktion definiert ist dynlm, wird die falsche Modellmatrix gebildet. Wenn Sie versuchen zu debuggen, werden Sie feststellen, dass die verzögerte abhängige Variable im Fall der angegebenen newdataArgumentation nicht verzögert wird.

Sie können die abhängige Variable verzögern und in die Variable aufnehmen newdata. Hier ist der Code, der diesen Ansatz veranschaulicht. Ich benutze set.seedes also leicht reproduzierbar.

library(dynlm)

set.seed(1)
y<-arima.sim(model=list(ar=c(.9)),n=10) #Create AR(1) dependant variable
A<-rnorm(10) #Create independant variables
B<-rnorm(10)
C<-rnorm(10)
y<-y+.5*A+.2*B-.3*C #Add relationship to independant variables 
data=cbind(y,A,B,C)

#Fit linear model
model<-dynlm(y~A+B+C+L(y,1),data=data)

Hier ist das Buggy-Verhalten:

> predict(model)
       2        3        4        5        6        7        8        9       10 
3.500667 2.411196 2.627915 2.813815 2.468595 1.733852 2.114553 1.423225 1.470738 
> predict(model,newdata=data)
        1         2         3         4         5         6         7         8         9        10 
2.1628335 3.7063579 2.9781417 2.1374301 3.2582376 1.9534558 1.3670995 2.4547626 0.8448223 1.8762437 

Bilde die newdata

#Forecast fix.
A<-c(A,rnorm(1)) #Assume we already have 1-step forecasts for A,B,C
B<-c(B,rnorm(1))
C<-c(C,rnorm(1))

newdata<-ts(cbind(A,B,C),start=start(y),freq=frequency(y))

newdata<-cbind(lag(y,-1),newdata)
colnames(newdata) <- c("y","A","B","C")

Vergleichen Sie die Prognose mit der Modellanpassung:

> predict(model)
       2        3        4        5        6        7        8        9       10 
3.500667 2.411196 2.627915 2.813815 2.468595 1.733852 2.114553 1.423225 1.470738 
> predict(model,newdata=newdata)
       1        2        3        4        5        6        7        8        9       10       11 
      NA 3.500667 2.411196 2.627915 2.813815 2.468595 1.733852 2.114553 1.423225 1.470738 1.102367 

Wie Sie für historische Daten sehen können, stimmt die Prognose überein und das letzte Element enthält die Prognose für einen Schritt voraus.

mpiktas
quelle
Wie können Sie mit dem Fall umgehen, dass Sie zwei Verzögerungen in derselben Formel haben? lag(y,-1)+lag(y,-2)?
Hugh Perkins
1
Nun, dann funktioniert diese Lösung nicht. Sie müssen Ihre eigene Vorhersagefunktion schreiben.
mpiktas
Ah, das habe ich tatsächlich getan :-P
Hugh Perkins
1
Haben Sie darüber nachgedacht, es an Dynlm-Autoren zu senden? Es ist eine bizarre Situation, die Sie mit Dynlm nicht vorhersagen können.
mpiktas
Hmmm, Sie sagen, sie werden den Stackoverflow nicht auf magische Weise überwachen und Fehler beheben? Ich denke das ist wahrscheinlich wahr!
Hugh Perkins
2

Auf Anfrage von @ md-azimul-haque habe ich meinen 4 Jahre alten Quellcode durchgesehen und die folgende entsprechend benannte Funktion gefunden. Sie sind sich nicht sicher, ob @ md-azimul-haque danach sucht?

# pass in training data, test data,
# it will step through one by one
# need to give dependent var name, so that it can make this into a timeseries
predictDyn <- function( model, train, test, dependentvarname ) {
    Ntrain <- nrow(train)
    Ntest <- nrow(test)
    # can't rbind ts's apparently, so convert to numeric first
    train[,dependentvarname] <- as.numeric(train[,dependentvarname])
    test[,dependentvarname] <- NA
    testtraindata <- rbind( train, test )
    testtraindata[,dependentvarname] <- ts( as.numeric( testtraindata[,dependentvarname] ) )
    for( i in 1:Ntest ) {
       cat("predicting i",i,"of",Ntest,"\n")
       result <- predict(model,newdata=testtraindata,subset=1:(Ntrain+i-1))
       testtraindata[Ntrain+i,dependentvarname] <- result[Ntrain + i + 1 - start(result)][1]
    }
    testtraindata <- testtraindata[(Ntrain+1):(Ntrain + Ntest),dependentvarname]
    names(testtraindata) <- 1:Ntest
    return( testtraindata )
}
Hugh Perkins
quelle