The Capital Asset Pricing Model is given by;\[ER_{j,t} = \alpha_j + K_{rf,t} + \beta_j(K_{m,t} - K_{rf,t}) + \epsilon_{j,t} \] where \(ER_{j,t}\) is the expected return of investment, \(\alpha_j\) is the intercept of CAPM, \(K_{rf,t}\) is the risk-free rate, \(\beta_j\) is the slope of CAPM (beta of the investment), \(K_{m,t}\) is the stock market return (expected), \((K_{m,t} -K_{rf,t})\) is the market risk premium and, \(\epsilon_{j,t}\) is the error term.
\(ER_{j,t}\), is the expected return of stock in a regression model. The parameter \(\alpha_j\) is the intercept of CAPM and is assumed to be 0 for correct pricing of \(j^{th}\) asset. If, \(\alpha_j=0\) then there is a possibility of mispricing of which we can test the statistical significance of \(\alpha_j\) using p-value of 5%. Given time series for the expected return of an investment, risk-free rate and expected return on the market, one can calculate the market risk premium, which the difference between the stock market return and the risk-free rate.
# Load important libraries
library(tidyverse)
library(tidyquant)
library(timetk)
Apple is the chosen asset for this part. Below is the code used to download daily adjusted closing price from 19-03-2021 to 19-03-2022 form Yahoo’s finance website.
# Downloading Apple price using quantmod
getSymbols("AAPL",
from = '2021-03-21',
to = '2022-12-21',
warnings = FALSE,
auto.assign = TRUE)
## 'getSymbols' currently uses auto.assign=TRUE by default, but will
## use auto.assign=FALSE in 0.5-0. You will still be able to use
## 'loadSymbols' to automatically load data. getOption("getSymbols.env")
## and getOption("getSymbols.auto.assign") will still be checked for
## alternate defaults.
##
## This message is shown once per session and may be disabled by setting
## options("getSymbols.warning4.0"=FALSE). See ?getSymbols for details.
## [1] "AAPL"
# Convert into time series
AAPL = AAPL[, "AAPL.Adjusted"]
AAPL %>% head(5)
## AAPL.Adjusted
## 2021-03-22 122.6610
## 2021-03-23 121.8160
## 2021-03-24 119.3805
## 2021-03-25 119.8775
## 2021-03-26 120.4938
Now we can visualize the adjusted closing price of Apple.
#Plot Apple price series
plot(AAPL, main = "Daily adjusted closing price for Apple", xlab = "date", ylab = "Adjusted Price")
Now we compute the stock returns for AAPL.
# Compute log returns of the series
aapl = Return.calculate(AAPL, method = "log")
aapl %>% head(5)
## AAPL.Adjusted
## 2021-03-22 NA
## 2021-03-23 -0.006912565
## 2021-03-24 -0.020196109
## 2021-03-25 0.004154911
## 2021-03-26 0.005128251
# Plot Apple log return series
plot(aapl, main = "Percentage (%) change in price of Apple", ylab = "% Change in price")
Beta for an asset can be calculated using the covariance/variance method. In order to calculate this, we need expected return on NASDAQ 100 index.
# Downloading Apple price using quantmod
getSymbols("^GSPC",
from = '2021-03-21',
to = '2022-12-21',
warnings = FALSE,
auto.assign = TRUE)
## [1] "^GSPC"
# Convert into time series
GSPC = GSPC[, "GSPC.Adjusted"]
#Plot Nasdaq100 index series
plot(GSPC, main = "Daily adjusted closing price for SP500 index", xlab = "date", ylab = "Adjusted Price")
Now we compute the returns of the market index, NASDAQ 100.
# Compute log returns of the series
gspc = Return.calculate(GSPC, method = "log")
# Plot Apple log return series
plot(gspc, main = "Percentage (%) change in price of SP500 index", ylab = "% Change in price")
Now we need to create a table with stock returns and the benchmark
returns. We will use the left_join to create this
table.
# Combine returns into 1 data set; exclude 1st row which is NA
xy = cbind(aapl, gspc[,1][-1,])
#Relabel returns AAPL.ret and GSPC.ret
names(xy) = c('AAPL.ret', 'GSPC.ret')
xy %>% head(5)
## AAPL.ret GSPC.ret
## 2021-03-22 NA NA
## 2021-03-23 -0.006912565 -0.007660118
## 2021-03-24 -0.020196109 -0.005482337
## 2021-03-25 0.004154911 0.005226583
## 2021-03-26 0.005128251 0.016494419
#Convert annual rate to daily by dividing by 365 (#days per yr)
rf = 0.4/365
# Reduce benchmark return by daily risk free rate
xy[,2] = xy[,2] - rf
# Run CAPM
lm(AAPL.ret ~ GSPC.ret, data = xy)
##
## Call:
## lm(formula = AAPL.ret ~ GSPC.ret, data = xy)
##
## Coefficients:
## (Intercept) GSPC.ret
## 0.001937 1.247700
xy %>%
ggplot(aes(x = GSPC.ret,
y = AAPL.ret)) +
geom_point(color = "blue") +
geom_smooth(method = "lm", # Display a line of best fit
se = FALSE,
color = "red")+
theme_classic() +
labs(x = 'SP500 Index Returns',
y = "APPLE Returns",
title = "APPLE returns vs SP500 index returns") +
scale_x_continuous(breaks = seq(-0.1,0.1,0.01),
labels = scales::percent) +
scale_y_continuous(breaks = seq(-0.1,0.1,0.01),
labels = scales::percent)
## `geom_smooth()` using formula 'y ~ x'