HAR-RV in R (highfrequency)¶

The R corner of the HAR trio (from-scratch → PyMC → R)¶

R's highfrequency package (Boudt, Cornelissen, Payseur et al.) is the standard toolkit for realized-volatility work — realized-measure estimators (rCov, bipower variation, realized kernels) and HARmodel, which fits Corsi's HAR in a single call. We fit the same log-HAR and confirm it reproduces the from-scratch, lm, and PyMC estimates.

In [1]:
suppressMessages({library(highfrequency); library(xts)})
d <- read.csv('spx_rv_ret.csv'); dates <- as.Date(d$date)
l <- log(d$rv * 1e4)                                     # log realized variance (%^2)
lrv <- xts(l, order.by = dates)
ntr <- floor(0.6 * (length(l) - 22)) + 22                # same 60% train split as the Python notebooks

fit <- HARmodel(lrv[1:ntr], periods = c(1, 5, 22), type = 'HAR', h = 1, transform = NULL)
cat('highfrequency::HARmodel coefficients (log-HAR, train):\n'); print(round(coef(fit), 3))
cat('\ncross-check -> from-scratch OLS / PyMC NUTS / lm() all give:',
    '\n   daily (RV1) 0.255   weekly (RV5) 0.491   monthly (RV22) 0.198\n')
Warning message:
"package 'highfrequency' was built under R version 4.6.1"
highfrequency::HARmodel coefficients (log-HAR, train):
(Intercept)         RV1         RV5        RV22 
     -0.027       0.255       0.491       0.198 
cross-check -> from-scratch OLS / PyMC NUTS / lm() all give: 
   daily (RV1) 0.255   weekly (RV5) 0.491   monthly (RV22) 0.198

The fit, and the wider highfrequency toolkit¶

In [2]:
options(repr.plot.width = 11, repr.plot.height = 4.3)
n <- length(l); T <- 23:n
X <- cbind(1, l[T - 1],
           sapply(T, function(t) mean(l[(t - 5):(t - 1)])),
           sapply(T, function(t) mean(l[(t - 22):(t - 1)])))
b <- coef(fit); fitted_all <- as.numeric(X %*% b); y_all <- l[T]
tr <- 1:(ntr - 22); R2 <- 1 - var(y_all[tr] - fitted_all[tr]) / var(y_all[tr])
cat('in-sample R^2 (log RV):', round(R2, 3), '\n')

rvol_act <- sqrt(252 * exp(y_all)); rvol_fit <- sqrt(252 * exp(fitted_all))   # exp(y) is RV in %^2 already
plot(dates[T], rvol_act, type = 'l', col = 'grey70', lwd = 0.5, xlab = '',
     ylab = 'annualized realized vol (%)',
     main = 'highfrequency::HARmodel fit vs actual realized volatility (2000-2013)')
lines(dates[T], rvol_fit, col = 'firebrick', lwd = 0.8)
legend('topright', c('actual RVol', 'HAR fitted'), col = c('grey60', 'firebrick'), lwd = c(1, 1.5), bty = 'n')
in-sample R^2 (log RV): 0.673 
No description has been provided for this image

Results¶

  • Three engines, one model. highfrequency::HARmodel returns exactly the same coefficients as the from-scratch OLS and PyMC's NUTS (daily 0.255, weekly 0.491, monthly 0.198), with $R^2=0.67$ on log RV — and because HARmodel is just OLS on the HAR regressors, base-R lm gives the identical fit. The HAR estimate is not an artifact of any one implementation.
  • The natural R home for the whole phase. highfrequency also provides the Phase-1 realized measures (rCov, bipower variation via rBPCov, realized kernels) and the HAR extensions (HARmodel(..., type = "HARQ"), jump components) as built-ins — the place to take realized-volatility modelling further in R.

This completes the HAR-RV trio: from-scratch (OLS + conjugate Bayes + out-of-sample vs GARCH), PyMC (NUTS + model comparison), and R (the canonical highfrequency package).

Reference¶

  • Corsi, F. (2009). A simple approximate long-memory model of realized volatility. J. Financial Econometrics 7, 174–196.
  • Boudt, K., Cornelissen, J., Payseur, S. et al. highfrequency: Tools for Highfrequency Data Analysis (R package).