You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Pine Script策略回测无订单生成问题求助

Pine策略无订单生成问题排查

我是Pine语言新手,具备类C语言开发经验,编写的首版回测策略无编译错误,但回测区间内始终无法生成订单。起初怀疑时间范围问题,已通过timestamp(string)设置覆盖全时段,仍无法定位问题。代码顶部注释说明了策略逻辑,恳请帮忙排查。

策略代码如下:

//@version=5
//This strategy has simple rules
//LONG when 
//1. the price closes below the EMA200
//2. the price closes above the Trend Trader Strategy by HPotter line (an alternative strategy is for the close price that crosses over the TTS line  in the previous bar - currently commnted out for testing)
//3. the STC Indicator by shayankm is green
//SHORT when
//1. the price closes above the EMA200
//2. the price closes below the Trend Trader Strategy by HPotter line (an alternative strategy is for the close price that crosses below the TTS line in the previous bar - currently commnted out for testing)
//3. the STC Indicator by shayankm is red
//CLOSE when
//the next bar closes (This strategy is intended to be tested for high frequency trading on 1-5 minute time frames or binary options)



strategy("Trend Trader Strategy with STC Indicator", overlay=true, initial_capital=1000, commission_type=strategy.commission.percent, commission_value=0.1, calc_on_every_tick=true, default_qty_type=strategy.percent_of_equity, default_qty_value=2, currency=currency.USD, pyramiding=0, backtest_fill_limits_assumption=0, slippage=0, process_orders_on_close=true, max_bars_back=100, linktoseries=false, shorttitle="")

// Backtesting Inputs
//startDate = input("0-01-01T00:00:00", "Start Date (YYYY-MM-DD)")
//endDate = input("2022-12-31T23:59:59", "End Date (YYYY-MM-DD)")

// Convert start and end dates to timestamps
startDateTimeStamp = timestamp("Jan 01 1900 00:00:00")
endDateTimeStamp = timestamp("Jan 01 2100 00:00:00")

// Calculate EMA 200
ema200 = ta.ema(close, 200)

// Trend Trader Strategy by HPotter
Length = input.int(21, minval=1)
Multiplier = input.float(3, minval=0.000001)
avgTR = ta.wma(ta.atr(1), Length)
highestC = ta.highest(Length)
lowestC = ta.lowest(Length)
hiLimit = highestC[1] - avgTR[1] * Multiplier
loLimit = lowestC[1] + avgTR[1] * Multiplier
trendLine = 0.0
pos = 0.0
trendLine := close > hiLimit and close > loLimit ? hiLimit :
             close < loLimit and close < hiLimit ? loLimit : nz(trendLine[1], close)
pos := close > trendLine[1] ? 1 : close < trendLine[1] ? -1 : nz(pos[1], 0)

// STC Indicator by shayankm
EEEEEE = input(12, 'Length')
BBBB = input(26, 'FastLength')
BBBBB = input(50, 'SlowLength')

AAAA(BBB, BBBB, BBBBB) =>
    fastMA = ta.ema(BBB, BBBB)
    slowMA = ta.ema(BBB, BBBBB)
    AAAA = fastMA - slowMA
    AAAA

AAAAA(EEEEEE, BBBB, BBBBB) =>
    AAA = input(0.5)
    var CCCCC = 0.0 //persistent variables
    var DDD = 0.0//persistent variables
    var DDDDDD = 0.0//persistent variables
    var EEEEE = 0.0//persistent variables
    BBBBBB = AAAA(close, BBBB, BBBBB)
    CCC = ta.lowest(BBBBBB, EEEEEE)
    CCCC = ta.highest(BBBBBB, EEEEEE) - CCC
    CCCCC := CCCC > 0 ? (BBBBBB - CCC) / CCCC * 100 : nz(CCCCC[1])
    DDD := na(DDD[1]) ? CCCCC : DDD[1] + AAA * (CCCCC - DDD[1])
    DDDD = ta.lowest(DDD, EEEEEE)
    DDDDD = ta.highest(DDD, EEEEEE) - DDDD
    DDDDDD := DDDDD > 0 ? (DDD - DDDD) / DDDDD * 100 : nz(DDDDDD[1])
    EEEEE := na(EEEEE[1]) ? DDDDDD : EEEEE[1] + AAA * (DDDDDD - EEEEE[1])
    EEEEE

mAAAAA = AAAAA(EEEEEE, BBBB, BBBBB)
mColor = mAAAAA > mAAAAA[1] ? color.new(color.green, 20) : color.new(color.red, 20)

// Entry conditions for short positions
enterShort = close < trendLine[1] and ema200 > close and mColor == color.red //the close for every position under the trend line
//enterShort = ta.crossunder(close, trendLine) and ema200 > close and mColor == color.red //the close from the crossunder of the trend line

// Entry conditions for long positions
enterLong = close > trendLine[1] and ema200 < close and mColor == color.green //the close for every position under the trend line
//enterLong = ta.crossover(close, trendLine) and ema200 < close and mColor == color.green //the close from the crossover the trend line

// Execute short trades
if time >= startDateTimeStamp and time < endDateTimeStamp and enterShort 
    strategy.entry("Short", strategy.short)
    //alert("Sell Short", alert.freq_once_per_bar_close)

// Execute long trades
if time >= startDateTimeStamp and time < endDateTimeStamp and enterLong
    strategy.entry("Long", strategy.long)
    //alert("Buy Long", alert.freq_once_per_bar_close)

// Close positions at the close of the next bar
if barstate.islast
    if strategy.position_size[0] < 0 and barstate.isconfirmed
        strategy.close("Short")

    if strategy.position_size[0] > 0 and barstate.isconfirmed
        strategy.close("Long")

核心问题及修正方案

1. 入场条件与策略规则完全反向

策略注释中明确做多条件第一条是价格收盘价低于EMA200,但代码中写的是ema200 < close(收盘价高于EMA200);做空条件第一条是价格收盘价高于EMA200,代码中写的是ema200 > close(收盘价低于EMA200),这直接导致入场条件永远无法满足。

修正后的入场条件:

// Entry conditions for short positions
enterShort = close < trendLine[1] and ema200 < close and (mAAAAA < mAAAAA[1])
// Entry conditions for long positions
enterLong = close > trendLine[1] and ema200 > close and (mAAAAA > mAAAAA[1])

2. STC颜色判断逻辑错误

color.new()会生成新的颜色对象,和原始color.red/color.green不是同一引用,用mColor == color.red判断永远为false。应直接通过指标值的变化趋势来判断(mAAAAA > mAAAAA[1]代表上涨绿色,mAAAAA < mAAAAA[1]代表下跌红色),无需通过颜色变量间接判断。

3. 平仓逻辑无效

barstate.islast和barstate.isconfirmed无法同时成立(最后一根K线未确认时islast为true,确认后islast会切换到下一根K线),导致平仓代码永远不会执行。若要实现“下一根K线收盘平仓”,可以在入场后直接用strategy.exit设置平仓规则:

修正后的平仓逻辑:

// 执行多单时,设置下一根K线收盘价平仓
if time >= startDateTimeStamp and time < endDateTimeStamp and enterLong
    strategy.entry("Long", strategy.long)
    strategy.exit("Exit Long", "Long", limit=close, stop=close)

// 执行空单时,设置下一根K线收盘价平仓
if time >= startDateTimeStamp and time < endDateTimeStamp and enterShort
    strategy.entry("Short", strategy.short)
    strategy.exit("Exit Short", "Short", limit=close, stop=close)

内容的提问来源于stack exchange,提问作者Judah Smith

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.19 22:47:01