研究实时警报重置初始化变量,但在历史数据上效果很好

Study live alerts resets initialized variables, but on historical data it works well

为了获得警报,只有在研究中才有可能,我从一个策略中创建了一个研究,我故意不使用金字塔。警报设置为每收盘价执行一次。

因为研究没有金字塔选项,我在研究中编写了一个类似的功能来避免金字塔,如下所示:

  1. 初始化布尔变量 Last_is_longLast_is_short 以存储最后一步是多头还是空头
  2. 检查布尔值作为完整 longCondition 的一部分和完整 shortCondition
  3. 的一部分
  4. 我根据这样完整的条件做了一个alertcondition(),其中包括布尔值,因此

类似于:

//@version=4
study(title="MyStudy", shorttitle="MyStudy", overlay=true)
...
//VARIABLE INITIALIZATION:
var bool Last_is_long = false
var bool Last_is_short = false
...
longCondition = myLongCondition() and not(Last_is_long)
shortCondition = myShortCondition() and not(Last_is_short)
...
alertcondition(longCondition, title='Long', message='Long now!')
if longCondition
    label.new(time, close, text = "Long", color=color.lime, xloc = xloc.bar_time)
    Last_is_long := true
    Last_is_short := false
...
alertcondition(shortCondition, title='Short', message='Short now!')
if shortCondition
    label.new(time, close, text = "Short", color=color.red, xloc = xloc.bar_time)
    Last_is_long := false
    Last_is_short := true

查看图表时,它运行良好。然而,随着警报打开,看起来 Last_is_longLast_is_short 变量总是被重新初始化(因此,到 false),因为每个柱中都会出现警报。

修复它的一种方法是重新处理整个基础 myLongCondition()myShortCondition() 函数以避免本质上以某种方式金字塔形,但我没有看到一种方法不会再次陷入布尔值不应重新初始化。

有什么克服它的想法吗?

出于好奇:Studies with alerts 只是在每个下一个执行步骤重新初始化变量,这是否是一种已知和期望的行为?

=========================================

编辑(下面的完整脚本):

 // Licensing information: free as bird. A referral to me would be much appreciated, though.
// Description: meant to be used with BTCUSD (or XBTUSD) on 3 mins to 1h candles charts.
// Idea is to provide a tool to detect break-out's from a dead band around an EMA, and to detect back-in's to the dead band.
// Detection is fundamentally based on how much %, at least, a certain candle body has ruptured the dead band (adjustable).
// Long and short flags are placed on the chart, as well as the deadband. Can be used to generate alers.
// With minimal modifications, can be convert to a Strategy script.

// Following are ideas to play around if you want. Room for improvements:
//  - convert constants into inputs, and diversify thresholds assimetrically
//  - play around with wether or not using pyramiding (here pyramiding is blocked)
//  - look at several bars in a sequence, not only current

// © esturilio:
//  TV  : https://www.tradingview.com/u/esturilio/
//  SO  : https://whosebug.com/users/12678720/glauco-esturilio?tab=profile
//  GH  : esturilio
//  TW  : @esturilio

//@version=4
study(title="Deadband cross", shorttitle="DB-X", overlay=true)

// === INIT VARIABLES === (needed on Study because Studies don't know about pyramiding)
var bool Last_is_long = false
var bool Last_is_short = false

// Defining the EMA curve for visualization
emaLen = input(12, minval=1, title="EMA Length")
emaSrc = input(open, title="Source for EMA")
emaVal = ema(emaSrc, emaLen)
plot(emaVal, title="EMA", color=color.blue)

// Defining the deadbands:
var float SigmaVar = input(0.30, minval=0, title="% deadband") // band around EMA
SigmaUp = emaVal * (1 + SigmaVar/100)
SigmaDw = emaVal * (1 - SigmaVar/100)
plot(SigmaUp, title="Band+", color=color.orange)
plot(SigmaDw, title="Band-", color=color.orange)

// Definition of the threshold for cross detection:
bar_bodypercent_threshold = input(50,title="%bar threshold for cross detection")

// =============================================================================
// detect cross or already crossed situations:
n_bar_span = abs(close - open)

// following conditions will be used to detect a bullish situation
bull_cross() => (close > SigmaUp and open < SigmaUp) or (close > SigmaUp and open > SigmaUp)
bear_back_cross() => (close > SigmaDw and open < SigmaDw)

// following conditions will be used to detect a bearish situation
bear_cross() => (close < SigmaDw and open > SigmaDw) or (close < SigmaDw and open < SigmaDw)
bull_back_cross() => (close < SigmaUp and open > SigmaUp)


// =============================================================================
// Calculate bar% above SigmaUp when crossing upwards
percent_bar_above_SigmaUp = if bull_cross()
    (100*(( max(close,open) - SigmaUp)/n_bar_span))
else
    0

// Calculate bar% below SigmaUp when crossing back down
percent_bar_below_SigmaUp = if bull_back_cross()
    (100*(( SigmaUp - min(close,open))/n_bar_span))
else
    0

// Calculate bar% below SigmaDw when crossing downwards    
percent_bar_below_SigmaDw = if bear_cross()
    (100*(( SigmaDw - min(close,open))/n_bar_span))
else
    0

// Calculate bar% above SigmaDw when crossing back up
percent_bar_above_SigmaDw = if bear_back_cross()
    (100*((max(close,open) - SigmaDw)/n_bar_span))
else
    0

// =============================================================================
// FINAL TRIGGERNIG:

 //longCondition: either bull or back from bear
longCondition  = ((close > SigmaUp) and (percent_bar_above_SigmaUp >= bar_bodypercent_threshold)) or ((close < SigmaUp) and (percent_bar_above_SigmaDw >= bar_bodypercent_threshold))

 //shortCondition: either bear or back from bull 
shortCondition = ((close < SigmaDw) and (percent_bar_below_SigmaDw >= bar_bodypercent_threshold)) or ((close > SigmaDw) and (percent_bar_below_SigmaUp >= bar_bodypercent_threshold))


longConditionFull = longCondition and Last_is_long == false
alertcondition(longConditionFull, title='LongTrigger', message='LongTrigger')

if  longConditionFull
    //if converting to strategy, you can uncomment below line for activating orders:
    //strategy.entry("Long",strategy.long)

    //plot green arrow
    label.new(time, close, text = "L", style=label.style_labelup, yloc=yloc.belowbar, color=color.lime, xloc = xloc.bar_time)

    //make sure pyramiding is not allowed 
    Last_is_long := true
    Last_is_short := false


shortConditionFull = shortCondition and Last_is_short == false
alertcondition(shortConditionFull, title='ShortTrigger', message='ShortTrigger')

if shortConditionFull
    //if converting to strategy, you can uncomment below line for activating orders:
    //strategy.entry("Short",strategy.short)

    //plot red arrow
    label.new(time, close, text = "S", style=label.style_labeldown, yloc=yloc.abovebar, color=color.red, xloc = xloc.bar_time)

    //make sure pyramiding is not allowed 
    Last_is_long := false
    Last_is_short := true

//DEBUG & PLOTTING: 
 // Bull and back from bull
//plot(percent_bar_above_SigmaUp, title="%above EMA+s",color=color.green)
//plot(percent_bar_below_SigmaUp, title="%above EMA+s",color=color.olive)

 // Bear and back from bear
//plot(percent_bar_below_SigmaDw, title="%below EMA-s",color=color.red)
//plot(percent_bar_above_SigmaDw, title="%below EMA-s",color=color.fuchsia)

您的代码逻辑似乎很合理,并且警报在这里工作正常。也许您可以尝试使用此处包含的调试代码来验证您的状态:

//@version=4
study(title="MyStudy", shorttitle="MyStudy", overlay=true)

//VARIABLE INITIALIZATION:
var bool Last_is_long = false
var bool Last_is_short = false

barUp = close >= open
myLongCondition() => barUp and barUp[1]
myShortCondition() => not barUp and not barUp[1]

longCondition = myLongCondition() and not(Last_is_long)
shortCondition = myShortCondition() and not(Last_is_short)

alertcondition(longCondition, title='Long', message='Long now!')
if longCondition
    label.new(time, close, text = "Long", color=color.lime, xloc = xloc.bar_time)
    Last_is_long := true
    Last_is_short := false

alertcondition(shortCondition, title='Short', message='Short now!')
if shortCondition
    label.new(time, close, text = "Short", color=color.red, xloc = xloc.bar_time)
    Last_is_long := false
    Last_is_short := true

bgcolor(Last_is_long ? color.green : Last_is_short ? color.maroon : na) 
plotchar(Last_is_long, "Last_is_long", "", location.top)
plotchar(Last_is_short, "Last_is_short", "", location.top)
plotchar(longCondition, "longCondition", "▲", location.top)
plotchar(shortCondition, "shortCondition", "▼", location.bottom)

如用户手册中所述here,实时柱中的变量通过回滚过程进行重置,但这只会影响实时柱中的行为,不会影响配置为触发 "Once Per Bar Close".

的警报