r - 量化贸易统计产生-100%的累积回报?



我在Quantstrat上使用贸易统计数据,获得了看起来与众不同的正期末股票(起始净值= 1m)。然而,令人费解的是,当我列出业绩表格时,累积回报是-1.0。

您如何才能拥有正的期末净值和负的累积回报?我对结束股权的理解是错误的吗?

library(quantmod)
library(FinancialInstrument)
library(PerformanceAnalytics)
library(foreach)
library(blotter)
library(quantstrat)
options("getSymbols.yahoo.warning"=FALSE)
options("getSymbols.warning4.0"=FALSE)
initDate="1990-01-01"
from ="2009-01-01"
to ="2013-01-01"
symbols = c("SPY")
currency("USD")
getSymbols(symbols, from=from, to=to, adjust=TRUE)
stock(symbols, currency="USD", multiplier=1)
initEq=1000000
strategy.st <- portfolio.st <- account.st <- "mystrat"
rm.strat(portfolio.st)
rm.strat(account.st)

initPortf(name=portfolio.st,
symbols=symbols,
initDate=initDate,
currency='USD')
initAcct(name=account.st,
portfolios=portfolio.st,
initDate=initDate,
currency='USD',
initEq=initEq)
initOrders(portfolio=portfolio.st,
initDate=initDate)
strategy(strategy.st, store=TRUE)
### Add Indicators
nRSI <- 21
buyThresh <- 50
sellThresh <- 50
#Indicator for EMA long medium short
nEMAL<- 200
nEMAM<- 30
nEMAS<- 13
nEMAF<- 5
add.indicator(strategy.st, name="RSI",
arguments=list(price=quote(Cl(mktdata)), n=nRSI),
label="rsi")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAL),
label="EMAL")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAM),
label="EMAM")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAS),
label="EMAS")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAF),
label="EMAF")
upsig <- function(data) {
sig <- data[, "rsi"] >50 & data[, "EMA.EMAM"] > data[, "EMA.EMAL"]   
colnames(sig) <- "upSig"
sig
}
downsig <- function(data) {
sig <- data[, "rsi"] <50 & data[, "EMA.EMAM"] < data[, "EMA.EMAL"]   
colnames(sig) <- "downSig"
sig
}

### Add Signal- Enter
add.signal(strategy.st, name="upsig",
arguments=list(data = quote(mktdata)),
label = "entersig")
add.signal(strategy.st, name="downsig",
arguments=list(data = quote(mktdata)),
label = "exitsig")
### Add rule - Enter
add.rule(strategy.st,
name='ruleSignal',
arguments = list(sigcol="upSig.entersig",
sigval=TRUE,
orderqty=1000,
ordertype='market',
orderside='long',
threshold=NULL),
type='enter',
path.dep=TRUE)

### Add rule- Exit
add.rule(strategy.st,
name='ruleSignal',
arguments = list(sigcol="downSig.exitsig",
sigval=TRUE,
orderqty= -1000,
ordertype='market',
orderside='long',
pricemethod='market',
replace=FALSE),
type='exit',
path.dep=TRUE)
start_t<-Sys.time()
out<-try(applyStrategy(strategy=strategy.st,
portfolios=portfolio.st))

updatePortf(portfolio.st)
updateAcct(portfolio.st)
updateEndEq(account.st)
for(symbol in symbols) {
chart.Posn(
Portfolio=portfolio.st,
Symbol=symbol,
log=TRUE)
}
tstats <- tradeStats(portfolio.st)
t(tstats)
rets <- PortfReturns(Account = account.st)
rownames(rets) <- NULL
charts.PerformanceSummary(rets, colorset = bluefocus)
tab.perf <- table.Arbitrary(rets,
metrics=c(
"Return.cumulative",
"Return.annualized",
"SharpeRatio.annualized",
"CalmarRatio"),
metricsNames=c(
"Cumulative Return",
"Annualized Return",
"Annualized Sharpe Ratio",
"Calmar Ratio"))
tab.perf

#Test here
#test <-try(applyIndicators(strategy.st,mktdata=OHLC(AAPL)))
#head(test, n=40)

首先,您只输入大量多头头寸。 然后是大量连续退出交易! 问题是您在很长一段时间内在每个信号条上都会收到长入场信号。而且您并没有限制您的策略进入越来越多的多头头寸,每个头寸的大小为 1000。 您可以使用osMaxPosaddPosLimit来处理在特定方向开仓时可能设置的交易数量上限。

以下是您可以停止在每个柱上发生如此多长条目的方法。 您希望当 rsi 上下穿过 50 时,该条目为真。 使用sigCrossover.其次,使用addPosLimit来限制允许的总头寸大小。 下次也查看mktdata以调试您的策略,检查您是否有多个入场信号。

你得到-1 暨回报,因为你提供了无意义的输入。 如此多的买入(您每连续一天在入场信号为真时买入 1k 个单位,然后连续卖出更多天)。 显然这不是故意的。 检查getTxns的输出以查看问题。 此外,您的最终资产可能是负数,因为您只是将投资组合中的现金盈亏添加到初始资本中。 即,一旦您的实际净值变为负值,Quantstrat 就不会停止交易。 你可以这样想:quantstrat只是继续交易,假设你有更多的资金可以交易,即使你的损失超过初始净值。

如果你输入合理的参数,你的净值永远不会在量化中变为负值(除非你的策略真的很糟糕并且一直亏损现金,或者你在回测中交易了很长时间,所以破产或更糟的概率在允许的时间内发生)。

以下是一些调整,即在您的策略中sigCrossover和使用 300 的交易规模,以获得更合理的数字。 还利用osMaxPos。 它仍然在这里购买最多 3 个级别的堆叠头寸。

library(quantmod)
library(FinancialInstrument)
library(PerformanceAnalytics)
library(foreach)
library(blotter)
library(quantstrat)
options("getSymbols.yahoo.warning"=FALSE)
options("getSymbols.warning4.0"=FALSE)
initDate="1990-01-01"
from ="2009-01-01"
to ="2013-01-01"
symbols = c("SPY")
currency("USD")
getSymbols(symbols, from=from, to=to, adjust=TRUE)
stock(symbols, currency="USD", multiplier=1)
initEq=1000000
strategy.st <- portfolio.st <- account.st <- "mystrat"
rm.strat(portfolio.st)
rm.strat(account.st)

initPortf(name=portfolio.st,
symbols=symbols,
initDate=initDate,
currency='USD')
initAcct(name=account.st,
portfolios=portfolio.st,
initDate=initDate,
currency='USD',
initEq=initEq)
initOrders(portfolio=portfolio.st,
initDate=initDate)
strategy(strategy.st, store=TRUE)
### Add Indicators
nRSI <- 21
buyThresh <- 50
sellThresh <- 50
#Indicator for EMA long medium short
nEMAL<- 200
nEMAM<- 30
nEMAS<- 13
nEMAF<- 5
tradeSize <- 100
for (sym in symbols) {
addPosLimit(portfolio.st, sym, start(get(sym)), maxpos = 300, longlevels = 3)
}
add.indicator(strategy.st, name="RSI",
arguments=list(price=quote(Cl(mktdata)), n=nRSI),
label="rsi")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAL),
label="EMAL")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAM),
label="EMAM")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAS),
label="EMAS")
add.indicator(strategy.st, name="EMA",
arguments=list(x=quote(Cl(mktdata)), n=nEMAF),
label="EMAF")
# important to set cross = TRUE in sigThreshold
add.signal(strategy.st, name = "sigThreshold",
arguments = list(column = "rsi", threshold = 50, relationship = "gt", cross = TRUE),
label = "rsiUp")
add.signal(strategy.st, name = "sigThreshold",
arguments = list(column = "rsi", threshold = 50, relationship = "lt", cross = TRUE),
label = "rsiDn")
upsig <- function(data) {
sig <- data[, "rsiUp"] & data[, "EMA.EMAM"] > data[, "EMA.EMAL"]   
colnames(sig) <- "upSig"
sig
}
downsig <- function(data) {
sig <- data[, "rsiDn"] & data[, "EMA.EMAM"] < data[, "EMA.EMAL"]   
colnames(sig) <- "downSig"
sig
}

### Add Signal- Enter
add.signal(strategy.st, name="upsig",
arguments=list(data = quote(mktdata)),
label = "entersig")
add.signal(strategy.st, name="downsig",
arguments=list(data = quote(mktdata)),
label = "exitsig")
### Add rule - Enter
add.rule(strategy.st,
name='ruleSignal',
arguments = list(sigcol="upSig.entersig",
sigval=TRUE,
orderqty=100,
ordertype='market',
orderside='long',
threshold=NULL,
osFUN = osMaxPos), # <- need this to cap trade levels to at most 3
type='enter',
path.dep=TRUE)

### Add rule- Exit
add.rule(strategy.st,
name='ruleSignal',
arguments = list(sigcol="downSig.exitsig",
sigval=TRUE,
orderqty= -100,
ordertype='market',
orderside='long',
pricemethod='market',
replace=FALSE),
type='exit',
path.dep=TRUE)
start_t<-Sys.time()
out<-try(applyStrategy(strategy=strategy.st,
portfolios=portfolio.st))

updatePortf(portfolio.st)
updateAcct(portfolio.st)
updateEndEq(account.st)
for(symbol in symbols) {
chart.Posn(
Portfolio=portfolio.st,
Symbol=symbol,
log=TRUE)
}
tstats <- tradeStats(portfolio.st)
t(tstats)
rets <- PortfReturns(Account = account.st)
rownames(rets) <- NULL
charts.PerformanceSummary(rets, colorset = bluefocus)
tab.perf <- table.Arbitrary(rets,
metrics=c(
"Return.cumulative",
"Return.annualized",
"SharpeRatio.annualized",
"CalmarRatio"),
metricsNames=c(
"Cumulative Return",
"Annualized Return",
"Annualized Sharpe Ratio",
"Calmar Ratio"))
tab.perf

tail(.blotter$account.mystrat$summary)
# Additions Withdrawals Realized.PL Unrealized.PL Interest Gross.Trading.PL Txn.Fees Net.Trading.PL Advisory.Fees Net.Performance  End.Eq
# 2012-12-20 19:00:00         0           0           0        -392.4        0        -392.4006        0      -392.4006             0       -392.4006 1012255
# 2012-12-23 19:00:00         0           0           0        -132.0        0        -131.9961        0      -131.9961             0       -131.9961 1012123
# 2012-12-25 19:00:00         0           0           0        -180.0        0        -180.0018        0      -180.0018             0       -180.0018 1011943
# 2012-12-26 19:00:00         0           0           0         -57.0        0         -57.0006        0       -57.0006             0        -57.0006 1011886
# 2012-12-27 19:00:00         0           0           0        -459.0        0        -458.9997        0      -458.9997             0       -458.9997 1011427
# 2012-12-30 19:00:00         0           0           0         714.0        0         714.0015        0       714.0015             0        714.0015 1012141

最新更新