Meridian Session Clock
- 程序库
- 版本: 1.0
- 激活: 5
一个 MQL4 时间函数库:在 UTC 与 12 个时区之间进行考虑夏令时的正确换算,建立经纪商服务器时钟的模型(可从价格历史自动识别),提供 Sydney、Tokyo、London、New York 交易时段以及您自定义的时段,包括开盘状态、开始与结束时间和 OHLC 区间,以及 FX 交易日和周末。与 TimeGMT() 不同,它在策略测试器中给出与实盘相同的结果。它从不交易、不绘图、不写文件。您获得的是编译后的 Meridian_Session_Clock.ex4;本页即完整的 API 参考。
快速开始
- 将 Meridian_Session_Clock.ex4 复制到 MQL4/Libraries(文件 > 打开数据文件夹)。
- 把下面的 #import 代码块粘贴到您的 EA、指标或脚本中。
- OnInit:MSC_DetectBroker("EURUSD", 104, base, conf, used);若已知服务器时钟,则用 MSC_SetBroker(MSC_US_DST, 120)。
- 使用服务器时间(TimeCurrent()、Time[i]):MSC_SessionIsOpen(MSC_LONDON_SESSION, TimeCurrent())。
- 验证:在策略测试器中运行下方示例;日志会在每根K线输出识别出的模型和 London 时段时间。
导入声明(可直接复制)
#import "Meridian_Session_Clock.ex4"
int MSC_ZoneOffset(int zone, datetime utc);
bool MSC_IsDST(int zone, datetime utc);
datetime MSC_ToZone(datetime utc, int zone);
datetime MSC_FromZone(datetime local, int zone);
datetime MSC_NextChange(int zone, datetime utc);
string MSC_ZoneName(int zone);
bool MSC_SetBroker(int model, int base_minutes);
int MSC_DetectBroker(string symbol, int weeks, int &base_minutes, double &confidence, int &weeks_used);
int MSC_BrokerOffset(datetime utc);
datetime MSC_ServerToUTC(datetime server_time);
datetime MSC_UTCToServer(datetime utc);
int MSC_SessionAdd(int zone, int start_minute, int end_minute, int days_mask);
void MSC_SessionClear();
string MSC_SessionName(int session);
bool MSC_SessionIsOpen(int session, datetime server_time);
datetime MSC_SessionStart(int session, datetime server_time, int index);
datetime MSC_SessionEnd(int session, datetime server_time, int index);
int MSC_SessionRange(string symbol, int timeframe, int session, datetime server_time, int index, double &result[]);
datetime MSC_TradingDayStart(datetime server_time);
bool MSC_IsWeekend(datetime server_time);
int MSC_LastError();
string MSC_ErrorText(int code);
#import
enum MSC_ZONE { MSC_UTC, MSC_LONDON, MSC_FRANKFURT, MSC_ATHENS, MSC_MOSCOW, MSC_DUBAI, MSC_SINGAPORE, MSC_TOKYO,
MSC_SYDNEY, MSC_WELLINGTON, MSC_NEW_YORK, MSC_CHICAGO };
enum MSC_MODEL { MSC_FIXED, MSC_US_DST, MSC_EU_DST };
enum MSC_SESSION { MSC_SYDNEY_SESSION, MSC_TOKYO_SESSION, MSC_LONDON_SESSION, MSC_NEW_YORK_SESSION }; 基本概念
- 三种时间:utc;server(经纪商服务器时间:TimeCurrent、K线时间);local(某时区的本地钟表时间)。
- 时区 0-11:UTC、London、Frankfurt、Athens、Moscow、Dubai、Singapore(也适用于香港、上海)、Tokyo、Sydney、Wellington、New York、Chicago。夏令时遵循各时区自 2000 年以来的法规,包括美国 2007、Sydney 2000 / 2006 / 2008、Auckland 2007 / 2008 和 Moscow 2011 / 2014 的调整。支持 2000-2099 年;其他时间按相同规则计算并标记 -2。
- 因夏令时开始而跳过、或因夏令时结束而重复的本地时间,按切换前生效的偏移读取(New York 三月切换日的 02:30 = 07:30 UTC;十一月切换日的 01:30 = 05:30 UTC,即第一次出现)。
- 经纪商时钟 = UTC + 偏移。模型:0 FIXED(全年为基准值),1 US DST(美国夏令时期间基准 + 60:"New York close" 经纪商,GMT+2 / GMT+3),2 EU DST(欧洲夏令时期间基准 + 60)。默认 1,基准 120。
- 时段以某时区的本地时间定义,按开始日为周一至周五:0 SYDNEY 07:00-16:00 Sydney,1 TOKYO 09:00-18:00 Tokyo,2 LONDON 08:00-17:00 London,3 NEW YORK 08:00-17:00 New York;自定义 id 为 4-15。一个实例从开始(含)持续到结束(不含)。index 0 = 在给定时间或之前开始的最近一个实例(进行中或已结束),-1 为上一个,+1 为下一个;范围 -260 至 260。
API 参考
所有函数都会设置 MSC_LastError。错误的时区或时段 id 返回 -1,并给出 0、false、"UNKNOWN" 或 -1。
MSC_ZoneOffset、MSC_IsDST、MSC_ToZone、MSC_FromZone
时区在 utc 时刻相对 UTC 的偏移(分钟);是否处于夏令时(Moscow 2011-2014 的永久 UTC+4 不算夏令时);utc + 偏移得到的本地时间;按上述规则把本地时间换回 UTC。
datetime ny = MSC_ToZone(MSC_ServerToUTC(TimeCurrent()), MSC_NEW_YORK);
MSC_NextChange 与 MSC_ZoneName
utc 之后的第一次偏移变化(UTC 时间),三年内没有则为 0(UTC、Dubai、Singapore、Tokyo、2014 年后的 Moscow)。时区名称,如上表所列。
MSC_SetBroker
model 0-2,base_minutes 为 -720 至 840,步长 15。否则返回 false 并设置 -1。
MSC_DetectBroker
读取 symbol("" = 图表品种)每个周末缺口(36 小时或以上)之后的第一根 H1 K线,从最新往回,最多 weeks 周(4-520,0 = 104)。FX 市场于周日 New York 时间 17:00 开盘,因此每周得到一个偏移;适合周数最多的模型和基准获胜(平局时:US DST,其次 EU DST,最后 FIXED)。若至少 60% 的周数吻合,则返回并应用该模型;否则返回 -1 并设置 -5 NOT DETECTED(base_minutes 和 confidence 仍会填写)。没有 H1 历史时为 -3 NO DATA。请使用 24/5 交易的主要 FX 货币对:贵金属和指数周日开盘较晚,会多读出一小时(测试中 XAUUSD 给出基准 180 而非 120)。请使用 52 周或更多,以包含夏令时切换;节假日周会降低置信度。在策略测试器中只能看到测试器加载的历史(weeks_used 表示读取了多少周)。
int base, used; double conf;
int model = MSC_DetectBroker("EURUSD", 104, base, conf, used); MSC_BrokerOffset、MSC_ServerToUTC、MSC_UTCToServer
utc 时刻服务器的偏移(分钟);服务器时间换算为 UTC(切换前后的那一小时按上述规则);UTC 换算为服务器时间。
MSC_SessionAdd、MSC_SessionClear、MSC_SessionName
添加时段:zone、本地午夜后的开始与结束分钟数(0-1439,二者不同;结束小于开始 = 跨夜),开始日的 days_mask(bit 0 周日至 bit 6 周六,62 = 周一至周五,1-127)。返回 id 4-15,或返回 -1 并设置 -1 或 -4 SESSION LIMIT。MSC_SessionClear 删除自定义时段(id 从 4 重新使用)。名称:SYDNEY、TOKYO、LONDON、NEW YORK、CUSTOM n。
int fra = MSC_SessionAdd(MSC_FRANKFURT, 7 * 60, 15 * 60 + 30, 62); // 07:00-15:30 Frankfurt
MSC_SessionIsOpen、MSC_SessionStart、MSC_SessionEnd
实例 0 是否包含 server_time;实例 index 开始或结束的服务器时间。出错时为 0。
if(MSC_SessionIsOpen(MSC_LONDON_SESSION, TimeCurrent()) && !MSC_SessionIsOpen(MSC_NEW_YORK_SESSION, TimeCurrent())) { } MSC_SessionRange
根据 symbol("" = 图表)在 timeframe(0 = 图表;M1、M5、M15、M30 或 H1)上开盘时间落在实例内的K线,计算实例 index 的 OHLC。result[] 得到 7 个值:0 开盘、1 最高、2 最低、3 收盘、4 首次到达最高价的K线时间、5 首次到达最低价的K线时间、6 K线数量。返回K线数量;实例内没有K线时返回 0 并设置 -3 NO DATA;timeframe、时段或 index 错误时返回 -1。进行中的实例使用目前已有的K线。
double r[]; if(MSC_SessionRange("", PERIOD_M15, MSC_TOKYO_SESSION, TimeCurrent(), -1, r) > 0) Print("Tokyo high ", r[1]); MSC_TradingDayStart 与 MSC_IsWeekend
server_time 当时或之前最近一次 New York 17:00 的服务器时间(FX 交易日开始)。周末 = New York 时间周五 17:00 至周日 17:00。
MSC_LastError 与 MSC_ErrorText
最后一次调用的代码;文本:0 OK,-1 INVALID PARAMETER,-2 OUT OF RANGE,-3 NO DATA,-4 SESSION LIMIT,-5 NOT DETECTED,其他为 UNKNOWN。
可运行的集成示例
一个智能交易系统(EA);请先粘贴上方的导入代码块和 enum 行。
datetime last = 0;
int OnInit()
{
int base, used; double conf;
int m = MSC_DetectBroker("EURUSD", 104, base, conf, used);
if(m < 0) MSC_SetBroker(MSC_US_DST, 120);
PrintFormat("model %d base %d conf %.2f weeks %d: %s", m, base, conf, used, MSC_ErrorText(MSC_LastError()));
return(INIT_SUCCEEDED);
}
void OnTick()
{
if(Time[0] == last) return;
last = Time[0];
datetime now = TimeCurrent();
PrintFormat("London %s - %s server, open %d, FX day since %s, weekend %d",
TimeToString(MSC_SessionStart(MSC_LONDON_SESSION, now, 0)), TimeToString(MSC_SessionEnd(MSC_LONDON_SESSION, now, 0)),
MSC_SessionIsOpen(MSC_LONDON_SESSION, now), TimeToString(MSC_TradingDayStart(now)), MSC_IsWeekend(now));
} 架构与说明
- 纯计算:规则是计算出来的,不是查表,因此不需要下载任何内容。经纪商模型和时段表按每个导入本函数库的程序分别保存。
- MetaTrader 4,任意品种和周期;EA、指标、脚本均可。在策略测试器和优化中安全:不使用 DLL、文件、网络请求、图表对象、定时器或全局变量。只有 MSC_DetectBroker 和 MSC_SessionRange 会读取K线。
- 限制:16 个时段(4 个内置),实例 index 为 -260 至 260,年份 2000-2099。
- 典型设置。时段过滤:只在 MSC_SessionIsOpen(MSC_LONDON_SESSION, now) 时交易。亚洲区间突破:在 London 开盘时对 MSC_TOKYO_SESSION 调用 MSC_SessionRange,index 0(此时 Tokyo 仍在开盘)。每日逻辑:在 MSC_TradingDayStart 重置。回测:在 OnInit 中调用 MSC_DetectBroker 或 MSC_SetBroker,切勿使用 TimeGMT()。
- 截图和视频展示的是基于本函数库构建的演示 EA;它不包含在购买内容中。
风险提示
时段时间描述的是市场通常活跃的时间,而不是价格将如何变动。请查看您经纪商的节假日安排;请先在模拟账户上测试。
