[R-SIG-Finance] Attempting to switch between instruments in quantstrat
Erol Biceroglu
erol.biceroglu at alumni.utoronto.ca
Sat Aug 13 06:26:41 CEST 2016
Hello,
I have another quantstrat-related question I was hoping someone could
help me with.
There's no error this time (at least I think), it's probably how I'm
setting it up, however any feedback would be greatly appreciated.
So, what I'm *trying* to do, is get quantstrat to chose an instrument
in mktdata to apply the rules to based on the value of a variable
(here **decileThreshold**). The idea is, if **decileThreshold** is
equal to 2, I only want to trade the 2nd instrument and ignore the
first. Thus, I load the indicator and signal as usual, and then add
*another* signal to check if the instrument equals
**decileThreshold**. Lastly, I then combine the previous signals with
**sigFormula** (which combines **decileThreshold** with the
indicator-signal) to generate the buy-rule.
The buy-rule, in theory, is only executed if the rule-signal is true
AND if the "instrument is equal to the **decileThreshold** threshold".
I'm trying to pack it all into one set of code since I *eventually*
want to optimize the volatility of the instrument. (I've cut out a lot
of stuff and have included only the bare minimum).
applyIndicators and applySignals work if I supply my own mktdata
matrix, where I really just merge the instruments.
What confuses me, is why applyRules works on the first instrument,
when my **decileThreshold** value should only make it applicable to
the second instrument?
This is likely extremely confusing, so please let me know how I can
clarify my objective any further.
Worst case, for my "real code", I have a work-around that involves
running each instrument separately within a for-loop. However, I was
hoping that I can get this to work so that I can leverage the
optimization functionality within quantstrat.
Any thoughts, comments, or feedback would be greatly appreciated.
Thank you,
Session Info:
> sessionInfo()
R version 3.3.1 (2016-06-21)
Platform: x86_64-pc-linux-gnu (64-bit)
Running under: Ubuntu 14.04.4 LTS
locale:
[1] LC_CTYPE=en_CA.UTF-8 LC_NUMERIC=C
LC_TIME=en_CA.UTF-8
[4] LC_COLLATE=en_CA.UTF-8 LC_MONETARY=en_CA.UTF-8
LC_MESSAGES=en_CA.UTF-8
[7] LC_PAPER=en_CA.UTF-8 LC_NAME=C
LC_ADDRESS=C
[10] LC_TELEPHONE=C LC_MEASUREMENT=en_CA.UTF-8
LC_IDENTIFICATION=C
attached base packages:
[1] stats graphics grDevices utils datasets methods base
other attached packages:
[1] quantstrat_0.9.1739 foreach_1.4.3
blotter_0.9.1695
[4] FinancialInstrument_1.2.0 quantmod_0.4-5
TTR_0.23-1
[7] PerformanceAnalytics_1.4.3541 xts_0.9.874
zoo_1.7-13
loaded via a namespace (and not attached):
[1] tools_3.3.1 codetools_0.2-14 grid_3.3.1 iterators_1.0.8
lattice_0.20-33
MRE:
####################
library(xts)
library(PerformanceAnalytics)
library(quantmod)
library(TTR)
library(quantstrat)
getSymbols(Symbols = "SPY")
SPY <- SPY$SPY.Close
#create a more volatile copy
tmp <- diff(SPY)
tmp <- 1.5*tmp
SPY2 <- cumsum(rbind(SPY[1,],tmp[-1,]))
colnames(SPY2) <- "SPY2.Close"
#There we go...
# head(SPY)
# head(SPY2)
#Rename to fit into my "existing" code:
MAPortfolio1 <- SPY
MAPortfolio2 <- SPY2
rm(SPY,SPY2)
colnames(MAPortfolio1) <- "MAPortfolio1"
colnames(MAPortfolio2) <- "MAPortfolio2"
########################
# All this block does is loop through the instruments, and append a
constant vector to it
for(item in paste0("MAPortfolio",1:2)){
tmp <- merge(get(item), rep(which(item ==
paste0("MAPortfolio",1:2)),nrow(get(item))))
colnames(tmp) <- c(paste0(colnames(tmp)[1],".Close")
,paste0("MAPortfolio",which(item ==
paste0("MAPortfolio",1:2)),".Ind")
)
command <- paste0("MAPortfolio",which(item ==
paste0("MAPortfolio",1:2))," <- ",quote(tmp))
eval(parse(text = command))
}
rm(tmp)
# head(MAPortfolio1)
# head(MAPortfolio2)
#########################
startDate<-as.Date(index(MAPortfolio1)[1], format="%Y-%m-%d")
endDate<-as.Date(index(last(MAPortfolio1)), format="%Y-%m-%d")
currency("USD")
stock(primary_id = c("MAPortfolio1"),currency = "USD")
stock(primary_id = c("MAPortfolio2"),currency = "USD")
#name
maStrategy <-"MAStrategy"
#Date, one day before prices
strategyDate <- min(index(MAPortfolio1)) - 1
#*******************************
#Used to reset for testing
#rm.strat(maStrategy)
#rm(mktdata)
#*******************************
NumSh<-1
decileThreshold <- 2
maLag <- 5
if (!exists('.blotter')) .blotter <- new.env()
if (!exists('.strategy')) .strategy <- new.env()
#init portfolio and account
initPortf(name = maStrategy
, symbols = as.list(paste0("MAPortfolio",1:2)) #as defined
in Financial instrument
, initDate = strategyDate
)
initAcct(name = maStrategy
,portfolios = maStrategy
,initDate = strategyDate
,initEq = 1
)
#order book, and strategy
initOrders(portfolio = maStrategy
, initDate = strategyDate
)
#position limits
addPosLimit(maStrategy, symbol = "MAPortfolio1", strategyDate, maxpos
= NumSh, longlevels = NumSh, minpos = 0)
addPosLimit(maStrategy, symbol = "MAPortfolio2", strategyDate, maxpos
= NumSh, longlevels = NumSh, minpos = 0)
strategy( maStrategy, store = TRUE)
###############################################
#add indicator
add.indicator(strategy = maStrategy
, name = "EMA"
, arguments = list(x =
quote(mktdata$MAPortfolio1.Close), n = quote(maLag))
, label = "MAPortfolioma1"
)
add.indicator(strategy = maStrategy
, name = "EMA"
, arguments = list(x =
quote(mktdata$MAPortfolio2.Close), n = quote(maLag))
, label = "MAPortfolioma2"
)
#################################################
#################################################
#MAPortfolio is greater than N-Lag Moving Average
add.signal(strategy = maStrategy
, name = "sigComparison"
, arguments = list(columns =
c("MAPortfolio1.Close","MAPortfolioma1")
, relationship = "gt"
)
, label = "MAPortfolio.gt.ma1"
)
add.signal(strategy = maStrategy
, name = "sigComparison"
, arguments = list(columns =
c("MAPortfolio2.Close","MAPortfolioma2")
, relationship = "gt"
)
, label = "MAPortfolio.gt.ma2"
)
#################################################
#MAPortfolio is less-than-equal-to N-Lag Moving Average
#################################################
add.signal(strategy = maStrategy
, name = "sigComparison"
, arguments = list(columns = c("MAPortfolio1.Close","MAPortfolioma1")
, relationship = "lte"
)
, label = "MAPortfolio.lte.ma1"
)
add.signal(strategy = maStrategy
, name = "sigComparison"
, arguments = list(columns = c("MAPortfolio2.Close","MAPortfolioma2")
, relationship = "lte"
)
, label = "MAPortfolio.lte.ma2"
)
#################################################
add.signal(strategy = maStrategy
, name = "sigThreshold"
, arguments = list(column = "MAPortfolio1.Ind"
, threshold = decileThreshold
, relationship = "eq"
)
, label = "MAPortfolio.dThresh1"
)
add.signal(strategy = maStrategy
, name = "sigThreshold"
, arguments = list(column = "MAPortfolio2.Ind"
, threshold = decileThreshold
, relationship = "eq"
)
, label = "MAPortfolio.dThresh2"
)
#################################################
#######
add.signal(strategy = maStrategy
, name = "sigFormula"
, arguments = list(formula = "MAPortfolio.dThresh1 == 1 &
MAPortfolio.gt.ma1 == 1")
, label = "MAPortfolio.sig.buy1"
)
add.signal(strategy = maStrategy
, name = "sigFormula"
, arguments = list(formula = "MAPortfolio.dThresh1 == 1 &
MAPortfolio.lte.ma1 == 1")
, label = "MAPortfolio.sig.sell1"
)
#######
#######
add.signal(strategy = maStrategy
, name = "sigFormula"
, arguments = list(formula = "MAPortfolio.dThresh2 == 1 &
MAPortfolio.gt.ma2 == 1")
, label = "MAPortfolio.sig.buy2"
)
add.signal(strategy = maStrategy
, name = "sigFormula"
, arguments = list(formula = "MAPortfolio.dThresh2 == 1 &
MAPortfolio.lte.ma2 == 1")
, label = "MAPortfolio.sig.sell2"
)
#######
#Entry and exit rules
#######
#buy MAPortfolio when above N-Lag Moving Average
add.rule(strategy = maStrategy
, name = "ruleSignal"
, arguments = list(sigcol = "MAPortfolio.sig.buy1"
, sigval = TRUE
, orderqty = NumSh
, ordertype = "market"
, orderside = NULL
, osFUN = "osMaxPos"
, symbol = "MAPortfolio1"
)
, type = "enter"
)
#sell MAPortfolio when above N-Lag Moving Average
add.rule(strategy = maStrategy
, name = "ruleSignal"
, arguments = list(sigcol = "MAPortfolio.sig.sell1"
, sigval = TRUE
, orderqty = "all"
, ordertype = "market"
, orderside = NULL
, osFUN = "osMaxPos"
, symbol = "MAPortfolio1"
)
, type = "exit"
)
#######
#######
#buy MAPortfolio when above N-Lag Moving Average
add.rule(strategy = maStrategy
, name = "ruleSignal"
, arguments = list(sigcol = "MAPortfolio.sig.buy2"
, sigval = TRUE
, orderqty = NumSh
, ordertype = "market"
, orderside = NULL
, osFUN = "osMaxPos"
, symbol = "MAPortfolio2"
)
, type = "enter"
)
#sell MAPortfolio when above N-Lag Moving Average
add.rule(strategy = maStrategy
, name = "ruleSignal"
, arguments = list(sigcol = "MAPortfolio.sig.sell2"
, sigval = TRUE
, orderqty = "all"
, ordertype = "market"
, orderside = NULL
, osFUN = "osMaxPos"
, symbol = "MAPortfolio2"
)
, type = "exit"
)
#######
mktdata <- merge(MAPortfolio1
, MAPortfolio2
)
applyIndicators(strategy = maStrategy, mktdata = mktdata)
applySignals(strategy = maStrategy, mktdata = mktdata)
#Why is this working, when decileThreshold == 2 ?
applyRules(portfolio = maStrategy
, symbol = "MAPortfolio1"
, strategy = maStrategy
, mktdata = mktdata
)
applyStrategy(strategy = maStrategy
, portfolios = maStrategy
#, mktdata = mktdata
)
#####################
Erol Biceroglu
erol.biceroglu at alumni.utoronto.ca
More information about the R-SIG-Finance
mailing list