Orthogonal IRF of VAR model
R code
The following R code loads yield curve data, calculates empirical yield factors, and estimates VAR(1) model using vars R package.
#========================================================# # Quantitative Financial Econometrics & Derivatives # Machine/Deep Learing, R, Python, Tensorflow # by Sang-Heon Lee # # https://shleeai.blogspot.com #--------------------------------------------------------# # Orthogonal Impulse Response #========================================================# graphics.off(); rm(list = ls()) library(vars) #----------------------------------------------------------- # Data : US Yield Curve 1972 - 2000 #----------------------------------------------------------- url <- 'https://www.dropbox.com/s/inpnlugzkddp42q/bonds.csv?dl=1' df <- read.csv(url, sep = ";") # Empirical yield factors L <- df[,"M120"] S <- df[,"M3"] - df[,"M120"] C <- 2 * df[,"M30"] - df[,"M3"] - df[,"M120"] # VAR endogenous variables data <- data.frame(L=L, S=S, C=C) nvar <- ncol(data) nobs <- nrow(data) vname <- colnames(data) head(data) #----------------------------------------------------------- # VAR estimation #----------------------------------------------------------- var.est <- VAR(data, p = 1, type = "const", season=NULL) var.summary <- summary(var.est) var.summary | cs |
> head(data) L S C 1 6.088 -2.706 0.730 2 6.283 -2.813 0.327 3 6.269 -2.395 1.037 4 6.240 -2.592 0.820 5 6.249 -2.414 0.272 6 6.301 -2.200 0.710 | cs |
The orthogonal impulse responses with 1 SD (standard deviation) shocks are easily calculated using the irf() function as follows.
#----------------------------------------------------------- # one SD shock IRF #----------------------------------------------------------- irf_1sd <- list() for (im in 1:nvar) { irf_1sd[[im]] <- irf(var.est, impulse = vname[im], n.ahead = 36, ortho = TRUE, boot = TRUE) windows(width = 4, height = 6) plot(irf_1sd[[im]], lwd = c(3,1,1), col = "black", main = paste0("1 SD orthogonal IRF from ", vname[im])) } | cs |
However, as far as I can tell, the irf() function does not provide the 1 unit shock IRFs. The IRFs based on 1 SD shock or 1 unit shock have the same shape, just different scales. In the latter case, the size of the shock is 1 unit, and since the unit of the variable used in this post is %, the 1 unit shock corresponds to the 1% shock. I calculate it by using the Cholesky decomposition as follows.
#----------------------------------------------------------- # one unit shock IRF #----------------------------------------------------------- # Cholesky decomposition for scaling # PP' = cov P = t(chol(var.summary$covres)) vscale <- diag(P); vscale irf_1ut <- list() for (im in 1:nvar) { irf_1ut[[im]] <- irf_1sd[[im]] # To make shock size 1 unit, dividing by diag(P) irf_1ut[[im]]$irf[[1]] <- irf_1ut[[im]]$irf[[1]]/vscale[im] irf_1ut[[im]]$Lower[[1]] <- irf_1ut[[im]]$Lower[[1]]/vscale[im] irf_1ut[[im]]$Upper[[1]] <- irf_1ut[[im]]$Upper[[1]]/vscale[im] windows(width = 4, height = 6) plot(irf_1ut[[im]], lwd = c(3,1,1), col = "blue", main = paste0("1 unit orthogonal IRF from ", vname[im])) } | cs |
It would be nice if the IRF plots generated by the irf() function were displayed in a matrix like EViews for multiple impulse shocks, but this is not the case. Therefore, we need to concatenate mannualy the IRF plots, which appear as a single column, horizontally,
In the next post, I'd like to discuss the IRF using the local projection of Jordà (2005), which takes nonlinearities into account to calculate IRFs.
No comments:
Post a Comment