Structural Breaks (Bull or Bear?)

[This article was first published on Timely Portfolio, and kindly contributed to R-bloggers]. (You can report issue about the content on this page here)
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.

When I spotted the bfast R package, I could not resist attempting to apply it to identify bull and bear markets.  For all the details that I do not understand, please see the references:

Jan Verbesselt, Rob Hyndman, Glenn Newnham, Darius Culvenor (2010). Detecting Trend and
  Seasonal Changes in Satellite Image Time Series. Remote Sensing of Environment, 114(1),
  106-115. doi:10.1016/j.rse.2009.08.014

Jan Verbesselt, Rob Hyndman, Achim Zeileis, Darius Culvenor (2010). Phenological Change
  Detection while Accounting for Abrupt and Gradual Trends in Satellite Image Time
  Series. Remote Sensing of Environment, 114(12), 2970 – 2980.
  doi:10.1016/j.rse.2010.08.003

I believe the result on the S&P 500 (even with a high h and only one iteration) is a fairly close marker for bull and bear markets, and I thoroughly enjoyed applying forestry techniques to financial time series.

From TimelyPortfolio
From TimelyPortfolio
From TimelyPortfolio

R code from GIST:

#analyze breakpoints with the R package bfast
#please read the paper
#Verbesselt J, Hyndman R, Newnham G, Culvenor D (2010)
#Detecting Trend and Seasonal Changes in Satellite Image Time Series.
#Remote Sensing of Environment, 114(1), 106–115.
#http://dx.doi.org/10.1016/j.rse.2009.08.014
require(bfast)
require(quantmod)
getSymbols("^GSPC",from="1950-01-01")
#convert to log price
GSPC.monthly <- log(to.monthly(GSPC)[,4])
#get monthly returns for the close price
#not necessary, leave in price form
#GSPC.return <- monthlyReturn(GSPC[,4])
#need ts representation so do some brute force conversion
GSPC.ts <- ts(as.vector(GSPC.monthly["1951-01::"]),start=c(1951,1),frequency=12)
#look at the stl Seasonal-Trend decomposition procedure already in R
GSPC.stl <- stl(GSPC.ts,s.window="periodic")
plot(GSPC.stl,main="STL Decomposition of S&P 500")
#get the results from bfast
#adjusting h lower will result in more breakpoints
GSPC.bfast <- bfast(GSPC.ts,h=0.2,max.iter=1,season="none")
plot(GSPC.bfast,type="components",ylim=c(3,max(GSPC.monthly)+1),main="S&P 500 with bfast Breakpoints and Components")
plot(GSPC.bfast,type="trend",ylim=c(3,max(GSPC.monthly)+1),main="S&P 500 with bfast Trend Breakpoints")
#see everything with type="all" but in bfast calculation set seasonal to "none"
#play away with this
#plot(GSPC.bfast,type="all")
#do some additional plotting
#[[1]] is used since for speed I only did one iteration
#could plot each iteration if I did multiple
plot(GSPC.bfast$Yt/GSPC.bfast$output[[1]]$Tt-1,
main="bfast Remainder as % of S&P 500 Price",
xlab=NA, ylab="remainder (% of price)",bty="l")
#add vertical line for the breakpoints
abline(v=breakdates(GSPC.bfast$output[[1]]$bp.Vt),col="gray70")
#add horizontal line at 0
abline(h=0,col="black",lty=2)
text(x=breakdates(GSPC.bfast$output[[1]]$bp.Vt),y=par("usr")[3]+.01,
labels=breakdates(GSPC.bfast$output[[1]]$bp.Vt,format.times=TRUE),
srt=90,pos=4,cex=0.75)

To leave a comment for the author, please follow the link and comment on their blog: Timely Portfolio.

R-bloggers.com offers daily e-mail updates about R news and tutorials about learning R and many other topics. Click here if you're looking to post or find an R/data-science job.
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.

Never miss an update!
Subscribe to R-bloggers to receive
e-mails with the latest R posts.
(You will not see this message again.)

Click here to close (This popup will not appear again)