Code: Select all
****************************************************************************************************************************
* This procedure allows the estimation of Bayesian VAR models with variable selection as outlined in Korobilis, D. (2011),
* VAR Forecasting Using Bayesian Variable Selection, Journal of Applied Econometrics, forthcoming.
*
* @BVARSELECTION( options ) start end forecasts
* # varlist
* # detlist
*
* start end - first and last period of estimation period
* forecasts - (optional) vector of series with point forecasts basedn on the restricted B-VAR
* varlist - list of variables of the VAR
* detlist - list of exogenous variables in the VAR
*
* OPTIONS:
* lags [1] - lag order of VAR
* nburns [1000] - number of initial convergence iterations for Gibbs sampler
* ndraws [1000] - number of iterations for Gibbs sampler
* ftime - forecasting time
* fsteps [12] - number of forecast steps
* [report]/noreport - determines if results are displayed
* graph/[nograph] - determines if forecasts are plotted
* bprior [not used] - provides values for prior means for the model coefficients (ord. like with RATS-VAR)
* gprior [.5] - prior for probability of inclusion of parameters
* rlprior [9.] - prior for lambda corresponding to coefficients of VAR lags (with ridge prior)
* rldetprior [100.] - prior for lambda corresponding to coefficients of exogenous variables (with ridge prior)
* mlprior [.1] - prior for lambda (with Minnesota prior)
*
* Written by Jonas Dovern (based on Matlab codes by D. Korobilis),
* Kiel Economics Research & Forecasting GmbH & Co. KG (www.kieleconomics.de),
* v0.9 - 11/2011.
*
****************************************************************************************************************************
source(noecho) mcmcpostproc.src
procedure BVARSELECTION start end forecasts
*
type integer start end
type vec[ser] *forecasts
*
option integer lags 1
option integer nburns 1000
option integer ndraws 1000
option integer ftime
option integer fsteps 12
option switch report 1
option switch graph 0
option choice prior 1 ridge minnesota
option vec bprior
option real gprior .5
option real rlprior 9.
option real rldetprior 100.
option real mlprior .1
*
local integer nvar ndet i j l draw periods hfi vfi lftime
local real p_j_tilde c d
local index varlist detlist
local rec x y x2 y2 D0 D0_inv eta eta_inv beta_OLS2 sse sigma V x_star beta_var beta2 theta2
local rec[int] dettable
local vec b0 p_j gamma beta_OLS beta ux theta theta_star theta_star_star beta_mean beta_stderrs gamma_mean theta_mean theta_cd uni_var
local vec[ser] fc_ols simfc fc_gibbs
local ser[vec] beta_draws gamma_draws theta_draws
local ser[rec] sigma_draws
local ser[int] permutation
local model VARmodel
local vec[str] rowlabels
*** Read varialbes and deterministic components from cards
enter(varying,entries=nvar) varlist
linreg(noprint) varlist(1)
comp detlist = %reglist(), dettable = %tablefromrl(detlist), ndet=%nreg
*** Check data availability and set forecasting time
inquire(regressorlist) i j
# varlist
if i>start-lags.or.j<end {
disp "There are missing data points in the sample you specified for the estimation!"
disp "(Pay attention to lags!)"
return
}
if %defined(bprior).and.%rows(bprior)<>lags*nvar*nvar+nvar*ndet {
disp "You provided a prior for beta (bprior) which does not have the right number of elements!"
return
}
comp lftime = %if(%defined(ftime),ftime,end+1)
*** Define model and produce OLS forecasts
system(model=VARmodel)
variables varlist
lags 1 to lags
det detlist
end(system)
estimate(noprint) start end
forecast(noprint,model=VARmodel,nostatic,from=lftime,steps=fsteps,results=fc_ols)
*** Construct data matrices
dim y2(end-start+1,nvar) x2(end-start+1,nvar*lags+ndet)
ewise y2(i,j) = ([series] varlist(j))(start-1+i)
comp y = %vec(y2)
do i=start,end
do j=1,nvar
do l=1,lags
comp x2(i-start+1,(j-1)*lags+l) = ([series] varlist(j))(i-l)
end do l
end do j
do j=1,ndet
comp x2(i-start+1,nvar*lags+j) = ([series] dettable(1,j))(i-dettable(2,j))
end do j
end do i
comp x = %kroneker(%identity(nvar),x2)
*** Set up arrays to hold the simulated parameters
gset beta_draws 1 ndraws = %zeros(lags*nvar*nvar+nvar*ndet,1)
gset gamma_draws 1 ndraws = %zeros(lags*nvar*nvar+nvar*ndet,1)
gset theta_draws 1 ndraws = %zeros(lags*nvar*nvar+nvar*ndet,1)
gset sigma_draws 1 ndraws = %zeros(nvar,nvar)
*** Define priors
if %defined(bprior)
comp b0 = bprior; * prior mean of beta
else {
if prior==1.or.prior==3
comp b0 = %zeros(lags*nvar*nvar+nvar*ndet,1)
else if prior==2 {
comp b0 = %zeros(lags*nvar*nvar+nvar*ndet,1)
ewise b0(i) = %if(%clock(i,lags*nvar+ndet)==1,1.,.0)
}
}
comp D0 = %identity(lags*nvar*nvar+nvar*ndet); * prior precision of beta
if prior==1
ewise D0(i,j) = D0(i,j)*%if(%clock(i,lags*nvar+ndet)<=lags*nvar,rlprior,rldetprior)
else if prior==2 {
* Getting error variance from univariate models
dim uni_var(nvar)
do k=1,nvar
linreg(noprint) varlist(k) start end
# constant varlist(k){1 to lags}
comp uni_var(k) = %SEESQ
end do k
* Filling prior matrix
do i=1,nvar
do j=1,lags*nvar+ndet
if %clock(j,lags*nvar+ndet)>lags*nvar
comp D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j) = D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j)*100*uni_var(i)
else if j>(i-1)*lags.and.j<=i*lags
comp D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j) = D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j)*%clock(j,lags)^2
else
comp D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j) = D0((i-1)*(lags*nvar+ndet)+j,(i-1)*(lags*nvar+ndet)+j)*(mlprior/%clock(j,lags)^2)*(uni_var(i)/uni_var(fix((j-1)/lags)+1))
end do j
end do i
}
comp D0_inv = inv(D0)
comp p_j = gprior*%ones(lags*nvar*nvar+nvar*ndet,1); * prior probability for inclusion of parameter
comp eta = %identity(nvar)
comp eta_inv = inv(eta)
*** Initialize parameters
comp gamma = %ones(lags*nvar*nvar+nvar*ndet,1)
comp beta_OLS = inv(tr(x)*x)*tr(x)*y
comp beta_OLS2 = inv(tr(x2)*x2)*tr(x2)*y2
comp sse = tr(y2-x2*beta_OLS2)*(y2-x2*beta_OLS2)
comp sigma = sse/((end-start+1)-lags*nvar-1)
dim ux(lags*nvar*nvar+nvar*ndet)
dim fc_gibbs(nvar)
*** Running Gibbs sampler
infobox(action=define,progress,lower=-nburns,upper=ndraws) "Running Gibbs sampler"
do draw=-nburns,ndraws
infobox(action=modify,current=draw)
*
comp V = %kroneker(inv(sigma),%identity(end-start+1))
comp x_star = %ones((end-start+1)*nvar,1)*tr(gamma).*x
*** Update beta
comp beta_var = inv(D0_inv+tr(x_star)*V*x_star)
comp beta = beta_var*(D0*b0+tr(x_star)*V*y) + %decomp(beta_var)*(ux=%ran(1.0))
comp beta2 = %vectorect(beta,lags*nvar+ndet)
*** Update gamma
boot(noreplace) permutation 1 lags*nvar*nvar+nvar*ndet 1 lags*nvar*nvar+nvar*ndet
do i=1,lags*nvar*nvar+nvar*ndet
comp theta = beta.*gamma
comp theta_star = theta
comp theta_star_star = theta
comp theta_star(permutation(i)) = beta(permutation(i))
comp theta_star_star(permutation(i)) = .0
comp c = p_j(permutation(i))*exp(%scalar(-gprior*tr(y-x*theta_star)*V*(y-x*theta_star)))
comp d = (1-p_j(permutation(i)))*exp(%scalar(-gprior*tr(y-x*theta_star_star)*V*(y-x*theta_star_star)))
comp p_j_tilde = c/(c+d)
comp gamma(permutation(i)) = %ranbernoulli(p_j_tilde)
end do i
comp gamma2 = %vectorect(gamma,lags*nvar+ndet)
comp theta2 = beta2.*gamma2
*** Update sigma
comp sigma = %ranwisharti(%decomp(inv(eta_inv+tr(y2-x2*theta2)*(y2-x2*theta2))),end-start+1-(lags*nvar+ndet))
*** Save draws and make forecasts
if draw>0 {
*** Save draws
comp beta_draws(draw) = beta
comp gamma_draws(draw) = gamma
comp theta_draws(draw) = theta
comp sigma_draws(draw) = sigma
*** Make forecasts
comp %modelsetcoeffs(VARmodel,theta2)
simulate(model=VARmodel,cv=sigma,results=simfc,from=lftime,steps=fsteps)
do i=1,nvar
set fc_gibbs(i) lftime lftime+fsteps-1 = %if(draw==1,simfc(i)(t),fc_gibbs(i)(t)+simfc(i)(t))
end do i
}
end do draw
infobox(action=remove)
*** Post simulation processing
if report {
do i=1,nvar
set fc_gibbs(i) lftime lftime+fsteps-1 = fc_gibbs(i)/ndraws
end do i
@MCMCPostProc(ndraws=ndraws,mean=theta_mean,cd=theta_cd) theta_draws
@MCMCPostProc(ndraws=ndraws,mean=beta_mean,stderrs=beta_stderrs) beta_draws
@MCMCPostProc(ndraws=ndraws,mean=gamma_mean) gamma_draws
}
*** Report output
if report {
dim rowlabels(lags*nvar*nvar+nvar*ndet)
do k=1,nvar
do j=1,nvar
do l=1,lags
comp rowlabels((k-1)*(lags*nvar+ndet)+(j-1)*lags+l) = %if(j==1.and.l==1,%l(varlist(k))+"_"+%l(varlist(j))+"{"+%string(l)+"}"," "+%l(varlist(j))+"{"+%string(l)+"}")
end do l
end do j
do j=1,ndet
comp rowlabels((k-1)*(lags*nvar+ndet)+nvar*lags+j) = " "+%l(dettable(1,j))+"{"+%string(dettable(2,j))+"}"
end do j
end do k
disp; disp "BVAR has been estimated over the period" %datelabel(start) "-" %datelabel(end) "."
report(action=define,vlabels=rowlabels,hlabels=||"","OLS-Beta","Beta*","Stderrs","Gamma**","Theta***","Geweke CD****"||)
report(action=modify,fillby=columns,atrow=1,atcol=2) beta_OLS
report(action=modify,fillby=columns,atrow=1,atcol=3) beta_mean
report(action=modify,fillby=columns,atrow=1,atcol=4) beta_stderrs
report(action=modify,fillby=columns,atrow=1,atcol=5) gamma_mean
report(action=modify,fillby=columns,atrow=1,atcol=6) theta_mean
report(action=modify,fillby=columns,atrow=1,atcol=7) theta_cd
report(action=format,picture="*.##")
report(action=show,title="Outputs from Gibbs sampler")
disp "* Mean of posterior density of beta."
disp "** Average posterior probability of the restiction index."
disp "*** Mean of posterior density of beta*gamma."
disp "**** Geweke CD for theta."
}
*** Plot forecasts
if graph {
inquire(seasonal) periods
@sethfiandvfi(number=nvar,hfi=hfi,vfi=vfi)
spgraph(hfi=hfi,vfi=vfi)
do k=1,nvar
graph(header=%l(varlist(k)),key=upleft,klabels=||"Data","OLS","Restr. B-VAR"||) 3
# varlist(k) %imax(start,end-periods*3) end; # fc_ols(k) lftime lftime+fsteps-1; # fc_gibbs(k) lftime lftime+fsteps-1
end do k
spgraph(done)
}
*** Return variables if requested
if %defined(forecasts) {
dim forecasts(nvar)
do k=1,nvar
set forecasts(k) lftime lftime+fsteps-1 = fc_gibbs(k)(t)
end do k
}
end procedure BVARSELECTION