保持敬畏之心
交易是一场持久战

Pine Script(129):判断K线是否落在自定义交易时段内

#Pine Script入门教学

判断K线是否落在自定义交易时段内

我们时常需要让脚本知道,当前的K线是否发生在一个特定的交易时段内。利用这些信息,我们可以实现例如仅在特定时间段内进行交易,或将警报限制在某个交易时段内等功能。

但Pine Script是如何判断一根K线是否落在某个特定的时间窗口内的呢?让我们看看如何用代码实现这一点。

自定义函数

Pine Script的 time() 函数可以判断脚本是否正在一个自定义时段内的K线上进行计算。该函数会返回两种值:当K线处于时段内时,它返回该K线的时间;如果K线处于时段外,我们则会得到 na 值。

就我们的目的而言,我们感兴趣的是 time() 返回na以外的值。因为那意味着K线正发生在该时段内。

我们通过下面这个自定义函数来利用这一特性:

// 当当前K线发生在指定的时段内时,InSession() 函数返回 'true',
// 并为给定的时区进行校正(可选)。
// 当K线不发生在该时间段内,或当图表时间周期为1天或更高时,
// 返回 'false'。 
InSession(sessionTime, sessionTimeZone=syminfo.timezone) =>
    not na(time(timeframe.period, sessionTime, sessionTimeZone))

这个 InSession() 函数有两个参数。第一个参数 sessionTime 通过一个Pine Script的时段字符串来定义时段的开始和结束时间。例如 "0800-1500",代表从8:00到15:00的时段。

另一个参数 sessionTimeZone 通过一个Pine Script的时区字符串来设定时段的时区。这是一个可选参数,在未设置时,默认使用交易品种的时区(syminfo.timezone)。一个可能的值是 "GMT+1",代表GMT+1时区。

在函数内部,我们进行了一个比较,当当前K线处于指定的时段和时区内时,该比较返回 true;当K线在该范围之外时,我们则得到 false

为了得到这个真/假结果,我们使用了几个代码元素。让我们从最内层的括号(( 和 ))开始,由内而外地进行分析。

我们使用了带有三个参数的 time() 函数。timeframe.period 使函数使用图表当前的时间周期。通过 sessionTimesessionTimeZone,我们将传给 InSession() 函数的值传递给了 time()

现在,time() 会返回K线的时间(当K线在时段内时)或者 na。虽然我们想知道K线是否发生在时段内,但我们对K线的时间本身不感兴趣,一个真/假的结果会更好用。

所以,我们将 time() 包装在 na() 函数内部。当 time() 返回 na 时(即K线在时段外),na() 会返回 true;当 time() 返回K线时间时(即K线在时段内),它返回 false

这样好一些了,但也和我们想要的结果相反:我们不希望在K线处于时段时得到 false 值。所以,我们在 na() 前面放上 not 运算符,它会返回相反的布尔值。现在,我们就能在K线处于时段内时得到 true,而在时段外时得到 false 了。

函数特性

使用 InSession() 函数时需要记住的一些事情:

  • 它在日线和更高的时间周期上总是返回 false。因为这些K线没有具体的时段信息,所以它们不可能发生在某个时间段内。
  • 图表上显示的K线时间可能与指定的时段不同,但该函数仍可能将它们识别为时段的一部分。这种情况发生在函数使用的时区与图表显示的时区不同时。
  • 该函数可能在时段内找不到任何一根K线。当设置的时段发生在交易品种的隔夜期间时(例如由于时区差异),这种情况就会出现。

函数范例

把上述函数加入脚本后,有多种方式可以使用它。

一个方便的使用方式是用我们希望测试的时段来调用该函数。例如,要查看当前K线是否发生在9:30到16:00之间,我们可以这样做:

// 查看当前K线是否落在上午9:30到下午4点的时段内
isInSession = InSession("0930-1600")

当我们也为函数提供一个时区时,它会进行时差转换来找到在该时区内的K线。例如,要为纽约(GMT-5)时间9:30到16:00时段内的K线背景上色,我们可以这样做:

// 检查当前K线是否在纽约时间9:30到16:00的时段内
inUSSession = InSession("0930-1600", "GMT-5")

// 为该时段内的K线设置红色背景
bgcolor(inUSSession ? color.new(color.red, 80) : na)

该函数也可以使用隔夜时段。比方说,我们想在17:15到1:00的时段内显示一条指数移动平均线。为此,当 InSession() 返回 true 时,我们使用 plot() 函数绘制该平均线,否则使用 na 值来禁用绘图:

// 只在17:15到1:00的时段内绘制移动平均线
emaValue = ta.ema(close, 20)
plot(InSession("1715-0100") ? emaValue : na, color=color.orange)

有时我们想知道当前K线具体发生在哪个时段。要做到这一点,我们可以多次调用 InSession(),每次用一个不同的时段进行检查。

例如,下面的代码会基于三个可能的交易时段来更改K线的颜色:

// 将0:00-6:00时段的K线设为绿色,9:00-12:00之间的设为蓝色,
// 13:00-17:30时段内的设为紫色,其他(作为默认)则为黄色
priceBarColour = if InSession("0000-0600")
    color.green
else if InSession("0900-1200")
    color.blue
else if InSession("1300-1730")
    color.purple
else
    color.yellow

barcolor(priceBarColour)

脚本范例

让我们来看看 InSession() 函数在完整脚本中是如何运作的。下面的指标会创建两种颜色的背景。

发生在指定时段和时区内的K线会获得蓝色背景,而不在该时段内的K线则使用黄色的图表背景。

该指标的完整代码如下:

//@version=5
indicator(title="See if bar falls in session", overlay=true)

// 当当前K线发生在指定的时段内时,InSession() 函数返回 'true',
// 并为给定的时区进行校正(可选)。
// 当K线不发生在该时间段内,或当图表时间周期为1天或更高时,
// 返回 'false'。 
InSession(sessionTime, sessionTimeZone=syminfo.timezone) =>
    not na(time(timeframe.period, sessionTime, sessionTimeZone))

// 创建输入项
session  = input.session("0900-1700", title="Session")
timeZone = input.string("GMT+1", title="Time Zone")

// 检查当前K线是否落在指定的时段内
bgcolor(InSession(session, timeZone) ? color.new(color.blue, 80) : na)

// 验证K线是否 *不* 发生在时段内
bgcolor(not InSession(session, timeZone) ? color.new(color.yellow, 70) : na)

我们以 indicator() 函数开始,用于命名该脚本并将其叠加显示在主图的交易品种上。

然后,我们引入了上面讨论过的自定义 InSession() 函数。

接下来,我们创建了两个输入项。第一个是时段输入(input.session()),我们用它来定义一个9:00到17:00的交易时段,并将其值存储在 session 变量中供后续使用。

另一个输入是字符串输入(input.string())。这个输入用于设定时段的时区,其默认值为 "GMT+1"。我们使用 timeZone 变量来追踪其当前值。

然后我们为时段内和时段外的K线背景上色:

// 检查当前K线是否落在指定的时段内
bgcolor(InSession(session, timeZone) ? color.new(color.blue, 80) : na)

// 验证K线是否 *不* 发生在时段内
bgcolor(not InSession(session, timeZone) ? color.new(color.yellow, 70) : na)

我们在这里两次调用了 bgcolor() 函数。每一次,条件运算符(?:)都会在 color.new() 函数创建的颜色和 na 值(用于关闭背景色)之间进行选择。

第一个背景色通过 InSession() 函数来判断当前K线是否落在我们用输入项设置的时段内。因此,我们使用 session 变量来获取‘Session’输入的当前值,并用 timeZone 变量获取‘Time Zone’输入的值。当K线处于该时间范围内时,条件运算符会返回一个透明的蓝色(color.blue),否则,传给 bgcolor()na 值会关闭背景。

另一个背景色则用于那些在时段内的K线。为了测试这一点,我们在 InSession() 前面放上 not 运算符。我们使用相同的参数调用该函数。当K线确实在时段之外时,背景会变为透明的黄色(color.yellow),否则,由于 na 的存在,背景色会被关闭。

图表示例

该指标在图表上看起来是这样的:

蓝色背景高亮了9:00-17:00 GMT+1时段内的K线。黄色背景则用于该范围之外的K线。

当我们将时段输入修改为一个从17:00到15:00的隔夜时段时,图表会变为:

现在只有两根K线处于时段之外(黄色背景),而几乎所有的K线都在时段之内(蓝色背景)。

需要记住的一件事是,图表和时段分别使用的是哪个时区。比方说,指标高亮的是9:00到17:00 (GMT+1) 时段内的K线,但图表的显示时区被设置为了UTC (GMT)。在这种情况下,脚本会高亮8:00到16:00(不含)这个时间范围内的K线:

虽然这乍一看似乎不正确,但它实际上是完全正确的:GMT时区中的8:00 K线,正好对应GMT+1时区的9:00点。

如果我们希望K线的时间戳与我们指定的时段相匹配,我们可以将图表的显示时区设置为与 InSession() 函数所使用的时区相同。

对于前面的例子,这意味着将图表切换到UTC+1时区,这样9:00的K线就会在我们告诉脚本要使用的9:00-17:00时段的开始时出现:

总结

  • time() 函数可以判断当前K线是否落在某个特定的时段内。如果是,该函数会返回一个非 na 的值。
  • 自定义的 InSession() 函数正是利用了这一特性。当K线处于给定的时段和指定的时区内时,InSession() 返回 true(否则返回 false)。
  • InSession() 和图表使用不同的时区时,K线的时间戳将与时段不匹配(但计算结果仍然是正确的)。
  • InSession() 可能在图表上找不到任何处于该时段内的K线。当设置的时段发生在交易品种的隔夜时间范围内时(例如由于时区差异),这种情况就会出现。
赞(0)
未经允许不得转载:图道交易 » Pine Script(129):判断K线是否落在自定义交易时段内
分享到

评论 抢沙发

登录

找回密码

注册