R/Log_Period_Vol.R

#' Log_Period_Vol
#'
#' @description Get data in a specified periodicity and output is excess return and scaled excess return.
#' Volatility is calculated using annualized exponential weighted average.
#'
#' @param listCoins List of cryptocurrencies in xts form with daily data frequency
#' @param listIndex List of index for dayly weekly and monthly frequency
#' @param period Periodicity of data. Can be "days", "weeks" or "months"
#' @param delta Delta used for volatility. Theses are always calculated using data and then transformed
#' @param annu Annualizing factor
#' @param dateRange Range for the different cryptocurrencies for output. Also final name for each list
#'
#' @return List with cryptocurrencies each with
#'  \item{name excessReturn}{description Timeseries of excess return}
#'  \item{name exReVol}{description Timeseries with excess return scaled by annulaized volatility}
#' @export
Log_Period_Vol <- function(listCoins = coinList.xts, listIndex = MSCI.xts,
                           period = c("days", "weeks", "months"),
                           delta = 60/61, annu = 365.25,
                           dateRange = list(
                             BitCoin = "2013/",
                             BitCash = "2017-08-01/",
                             Ethereum = "2016-02-01/",
                             Ripple = "2014-01-01/",
                             Cum = "2013/"
                           )) {
  cumMatrix <- do.call(cbind, sapply(listCoins, function(x) {
    diff(log(quantmod::Ad(x)))
  }))
  St <- 1 /(ncol(cumMatrix) - rowSums(is.na(cumMatrix)))
  cum_ind <- zoo::index(cumMatrix)
  cum.xts <- xts::xts(rowSums(cumMatrix, na.rm = TRUE) / St, order.by = cum_ind)

  cumPeriod <- do.call(cbind, sapply(listCoins, function(x) {
    AdPeriod <- xts::to.period(quantmod::Ad(x), period = period, last.of = TRUE) %>%
      quantmod::Cl() %>%
      log() %>%
      diff()
    # AdPeriod <- xts::period.apply(diff(log(quantmod::Ad(x))),
    #                             FUN = sum,
    #                             INDEX = xts::endpoints(quantmod::Ad(x),
    #                                                    on=period, k=1))
    }))
  Stp <- 1 /(ncol(cumPeriod) - rowSums(is.na(cumPeriod)))
  cum_ind_p <- zoo::index(cumPeriod)
  cumPeriod.xts <- xts::xts(rowSums(cumPeriod, na.rm = TRUE) / Stp, order.by = cum_ind_p)

  listCoins$Cum <- list(
    AdDay = cum.xts,
    re.log = cumPeriod.xts)

  outList <- sapply(listCoins, function(x) {
    if(any(class(x) != "list")) {
      AdDay <- quantmod::Ad(x)
      AdPeriod <- xts::to.period(AdDay, period = period, last.of = TRUE) %>%
        quantmod::Cl()
      re.log <- diff(log(AdPeriod))
      sd <- sqrt(ExpWeiVarCpp(diff(log(AdDay))[-which(is.na(diff(log(AdDay))))], delta, annu))
      # re.log <- xts::period.apply(diff(log(quantmod::Ad(x))),
      #                           FUN = sum,
      #                           INDEX = xts::endpoints(quantmod::Ad(x),
      #                                                  on=period, k=1))
      # sd <- sqrt(ExpWeiVarCpp(re.log[-which(is.na(re.log))], delta, annu))
    } else {
      AdDay <- x$AdDay
      re.log <- x$re.log
      re.log[re.log == 0 ] <- NA
      AdDay[AdDay == 0 ] <- NA
      sd <- sqrt(ExpWeiVarCpp(AdDay[-which(is.na(AdDay))], delta, annu))
      # sd <- sqrt(ExpWeiVarCpp(re.log[-which(is.na(re.log))], delta, annu))
    }
    MSCI_P <- diff(log(listIndex[[period]]))

    diff_Ad_sd <- nrow(AdDay) - length(sd)
    if(diff_Ad_sd > 0) {
      sd <- c(rep(NA, diff_Ad_sd), sd)
    }

    sdPeriod <- xts::xts(sd, order.by = zoo::index(AdDay)) %>%
      xts::to.period(period = period, last.of = TRUE) %>%
      quantmod::Cl()
    # sdPeriod <- xts::xts(sd, order.by = zoo::index(re.log)[-1])

    if(period == "weeks") {
      MSCI_ind <- zoo::index(MSCI_P) %>%
        as.character() %>%
        epitools::as.week()

      re.log_ind <- zoo::index(re.log) %>%
        as.character() %>%
        epitools::as.week()

      sdPeriod_ind <- zoo::index(sdPeriod) %>%
        as.character() %>%
        epitools::as.week()

      index <- dplyr::intersect(MSCI_ind$stratum3, re.log_ind$stratum3) %>%
        dplyr::intersect(sdPeriod_ind$stratum3) %>%
        lubridate::as_date()

      r_ind <- re.log_ind$stratum3 %in% index %>%
        which()
      r_dup <- (re.log_ind$stratum3[re.log_ind$stratum3 %in% index] %>%
                  duplicated() %>%
                  which())
      if(length(r_dup) != 0) {
        r_ind <- r_ind[-r_dup]
      }
      M_ind <- MSCI_ind$stratum3 %in% index %>%
        which()
      M_dup <- (MSCI_ind$stratum3[MSCI_ind$stratum3 %in% index] %>%
                  duplicated() %>%
                  which())
      if(length(M_dup) != 0) {
        M_ind <- M_ind[-M_dup]
      }
      s_ind <- sdPeriod_ind$stratum3 %in% index %>%
        which()
      s_dup <- (sdPeriod_ind$stratum3[sdPeriod_ind$stratum3 %in% index] %>%
                  duplicated() %>%
                  which())
      if(length(s_dup) != 0) {
        s_ind <- s_ind[-s_dup]
      }

      re.log <- xts::xts(re.log[r_ind], order.by = re.log_ind$stratum3[r_ind])
      MSCI_P <- xts::xts(MSCI_P[M_ind], order.by = MSCI_ind$stratum3[M_ind])
      sdPeriod <- xts::xts(sdPeriod[s_ind], order.by = sdPeriod_ind$stratum3[s_ind])

      excessReturn <- re.log - MSCI_P
      out <- cbind(excessReturn,
                   c(NA, as.numeric(excessReturn[-1]) / as.numeric(sdPeriod[-nrow(sdPeriod)])),
                   sdPeriod)
      colnames(out) <- c("excessReturn", "exReVol", "sigma")

    } else {
      index <- dplyr::intersect(as.character(zoo::index(re.log)),
                                as.character(zoo::index(MSCI_P))) %>%
        dplyr::intersect(as.character(zoo::index(sdPeriod))) %>%
        lubridate::as_date()

      excessReturn <- re.log[index] - MSCI_P[index]
      sdPeriod <- sdPeriod[index]
      out <- cbind(excessReturn,
                   c(NA, excessReturn[-1] / sdPeriod[-1]),
                   sdPeriod)
      colnames(out) <- c("excessReturn", "exReVol", "sigma")

    }

    return(out)
  })

  names(outList) <- stringr::str_extract_all(names(listCoins), pattern = "^.+(?=Yahoo)|Cum") %>%
    do.call(what = cbind) %>%
    as.vector()
  # Tested that this is slower: stringr::str_replace_all(names(listCoins), pattern
  # = "Yahoo.*$", "")

  out <- list(
    outList[[names(dateRange)[[1]]]][dateRange[[1]]],
    outList[[names(dateRange)[[2]]]][dateRange[[2]]],
    outList[[names(dateRange)[[3]]]][dateRange[[3]]],
    outList[[names(dateRange)[[4]]]][dateRange[[4]]],
    outList[[names(dateRange)[[5]]]][dateRange[[5]]]
  )
  names(out) <- names(dateRange)

  return(out)
}
3schwartz/SpecialeScrAndFun documentation built on May 4, 2019, 6:29 a.m.