私募

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz

期货量化软件:赫兹量化中锁定指标

[复制链接]
发表于 2024-4-4 08:08:25 | 显示全部楼层 |阅读模式
概述, p( d- I3 V2 R1 J" T% @, z, U
在上一篇文章我们曾做过一些修正和调整。 不过,依旧还有错误,如该文所附的视频所示。" g1 ~" `1 T7 q8 ]8 d7 I0 ~& ]
在本文中,我们将亲眼见证如何修复此错误。 虽然表面上看这似乎很简单,但我们需要遵循若干个步骤。 这个过程将是奇妙和有趣的。 我们的目标是令指标专门应用于特定的图表和品种。 即使用户尝试,他们也无法将指标应用于另外的图表,或在一个会话中多次打开它。
0 a0 N( d- |) _' c我鼓励您继续阅读,因为内容承诺非常实用。# I& V7 g, x2 m" L
将指标锁定在特定品种上。. P/ B2 \9 \' G5 Q. o  O6 U9 P
第一步是将控制指标链接到进行市场回放的品种。 这一步虽然看起来很简单,但对于开发我们的主要任务是必要的。 我们来看看指标代码在上下文中会是什么样子:/ K( K* J& @7 m" r6 ^# o* N& H" t
#property copyright "Daniel Jose") c" D" Z# f  Y4 h
#property indicator_chart_window6 G  @# L) m# s4 {( F% w* f( s  H
#property indicator_plots 0
+ r2 f8 V5 x' p" X0 t4 t! r$ v9 m//+------------------------------------------------------------------+
7 z( N# `( ?/ r% F; d9 j: _#include <Market Replay\C_Controls.mqh>
' p% [' e, ]0 k( k" I. `//+------------------------------------------------------------------+3 q; T7 g% P. N$ W
C_Controls      Control;1 U  |: _9 g# _  d! N  ^
//+------------------------------------------------------------------+! S9 y: ?3 Q7 X: Q
int OnInit()
3 g; U% g4 `9 N* S) h& T{
" |/ S( Y, j' N: {u_Interprocess Info;
3 ~2 g* `2 E& d+ d& E& D% `IndicatorSetString(INDICATOR_SHORTNAME, def_ShortName);1 @7 y+ F6 U" B
if (_Symbol != def_SymbolReplay)
: y  v- J6 e2 @{
0 S$ y" f3 B/ [% t9 MChartIndicatorDelete(ChartID(), 0, def_ShortName);
; F1 e, B6 Z0 N9 z' xreturn INIT_FAILED;
9 M; W7 j& O- R}
6 D) B! p7 A0 Q1 Iif (GlobalVariableCheck(def_GlobalVariableReplay)) Info.Value = GlobalVariableGet(def_GlobalVariableReplay); else Info.Value = 0;# _+ c2 F+ |6 ]& }! @8 b- o9 G
Control.Init(Info.s_Infos.isPlay);
' _* \) a3 h7 t9 ?! Z- T6 I& m: |; Greturn INIT_SUCCEEDED;
9 k0 q  V$ n& y}
) Z) O) g  ^+ E0 U//+------------------------------------------------------------------+8 P; @0 ]8 x% A8 M
int OnCalculate(const int rates_total, const int prev_calculated, const int begin, const double &price[])
3 g  \0 G6 W1 r% `{
# l. O( ^$ s1 P6 @. Oreturn rates_total;4 @/ M4 C0 \  N! ^/ z& g
}
' \8 g% j% d1 f//+------------------------------------------------------------------+
% P" g, g: H% A1 x5 k% D- [void OnChartEvent(const int id, const long &lparam, const double &dparam, const string &sparam)/ M! w4 e; o* s6 k0 B; k+ o
{
8 h# Z2 n8 H8 N. T7 d# BControl.DispatchMessage(id, lparam, dparam, sparam);9 N+ _% X5 i' x
}1 M7 X7 h2 r4 ?
//+------------------------------------------------------------------+" C1 l# p% r7 w7 C
void OnDeinit(const int reason)! ?/ p: V( i, n1 j# X! n
{
3 {: N0 v4 \" Xswitch (reason)
0 a* Z% j0 n# s  n{
0 {+ S, p: G! D3 S9 y# mcase REASON_REMOVE:8 y* T" R8 n, k( J8 x  X' B
case REASON_CHARTCLOSE:
0 ^( J7 M/ [* V3 h- V" Nif (_Symbol != def_SymbolReplay) break;4 V& u" z# P' V# y! N
GlobalVariableDel(def_GlobalVariableReplay);- f2 w$ N2 @* c, X
ChartClose(ChartID());) H/ ?) F3 H( ^- M% j( x$ N# c
break;
0 N! n  h$ ]  \0 }9 U" L. B  v}7 a, k+ [2 q: T# H  {
}2 z: x, V$ _/ U4 X
//+------------------------------------------------------------------+9 Q! Q* U* s8 B' y% a: t
我们首先检查针对的品种是否要进行市场回放。 如果不是这种情况,指标将自动关闭。 请注意,知道指标的名称很重要。 因此,初始化期间执行的第一个函数调用我们的指标,这令我们能够轻松删除它。
* s* S5 r+ J; N  c. G+ K现在重要的一点是:当您将其从图表中删除时,MetaTrader 5 会生成 DeInit 事件。 此事件触发 OnDeInit 函数,而标记为 REASON_REMOVE 的事件表示从图表中删除指标。 这是因为该品种与指标设计绑定的品种不同。 如果我们不重新检查并阻止代码运行,品种图表将关闭。 不过,幸亏我们的检查,它将保持开放状态。
6 t/ p$ n; Q  ]8 Z* U+ h  g如果指标代码与上一篇文章中提供的代码不同,请不要感到惊讶:上一篇文章重点在于其它改进和修复。 不过,在编写了文章和代码,并录制了本文随附的视频后,我意识到尽管其中一个问题已解决,但另一个问题仍未被发现。 这就是为什么我不得不修改代码。
% o, R1 g% B3 [) ^$ J尽管进行了修改,但我们不会在此处详述所做的全部修改。 必须删除很大一部分,因为它对于此处讨论的锁定方面无效。 因此,上面的代码与以前的代码有很大差别。 不过,我相信上一篇文章中讲演的知识在某些时候可能对某些人有用。 我保存了那篇文章,以表明有时我们都会犯错误,但我们依旧应该努力把事情做好。
" I& M  e. z0 h因此,我们来建立第一个锁定步骤,即确保控制指标仅存在于市场回放品种的图表上。 然而,该衡量值并不会阻止向同一图表或不同图表添加多个指标,因此必须进行调整。# s7 }& R) n% ]% g
我们应该避免在同一图表上多次使用指标。
1 C5 n, f. y; }我们已经解决了一个问题,现在我们来应对另一个问题。 这里有各种解决方案,这取决于我们真正想要和愿意做什么。 就个人而言,我没有看到这个问题的理想和最终解决方案。 不过,我将尝试提出一种方式,读者能感到熟悉和理解。 最重要的是,该解决方案将完全基于 MQL5。 我甚至考虑过使用外部编码的可能性,但最终决定使用纯 MQL5。 诉诸外部编码,并利用 DLL 进行锁定的想法很诱人,但这太容易了。
+ O  z' i4 q# f我认为在诉诸外部 DLL 来填补 MQL5 语言无法胜任的空白之前,我们在 MQL5 中还有很多东西需要学习。 这将提供一个在使用外部代码时看起来“更干净”的解决方案。 只是,这并无助于更好地理解 MQL5。 此外,这可能会强化 MetaTrader 5 是一个受限平台的误解。 对平台的误解和效力利用不足助长了这种误解。
# H8 W' y) X7 Z( I% t9 C  C为了应用我们提议的解决方案,您不得不进行一些修改,并撤回其它更改。 第一步是更改 InterProcess.mqh 头文件,令其拥有以下结构:
1 Y( ?1 t! S, \7 W3 }#property copyright "Daniel Jose"; j" ~" |8 P0 z
//+------------------------------------------------------------------+4 L; E9 H) W) {) H; ^- D5 v" H
#define def_GlobalVariableReplay        "Replay Infos"
2 A. _  p. N, {1 _5 E8 j0 ~" U2 W# C, g#define def_GlobalVariableIdGraphics    "Replay ID"
& {! ~% i2 L- ~3 L; _% y  h' \) o) ]0 ?2 o#define def_SymbolReplay                "RePlay"
5 ?# b4 y) k8 B% U#define def_MaxPosSlider                400
* u+ E$ K  I- X' q6 R#define def_ShortName                   "Market Replay", S7 x! i% U, H, M+ x6 I
//+------------------------------------------------------------------++ N6 Q$ j  |5 I, V7 {5 I
union u_Interprocess
# J. x; M' }1 t7 `& ?5 D# h{% x. F! k0 d. w" N( E9 h
union u_0
/ h6 L% T, i, U5 v6 W$ U: G{! o0 s: V5 N# S: M9 b9 k& ^
double  df_Value;% ?; ^* z6 ~# O( B4 R0 R% a( c
long    IdGraphic;
* A2 I$ d: X- j1 x; [' D}u_Value;
9 }. W: b$ g: F, Astruct st_0
1 ^+ o; [& Y( @1 L: b, c* V* O, Z{1 c* d- F4 v- [! `5 r, }
bool    isPlay;3 f- R: g' F# I. Y0 Z; f
int     iPosShift;
) E  `( P0 Q) t2 \6 h* E}s_Infos;
! P, D! X. F! h9 P3 _};
3 \) ^% T' c% N9 a//+------------------------------------------------------------------+; w% t& I" j2 D) a
对于许多不熟悉编程的人来说,这似乎有点奇怪,但令人惊讶的是,上述结构仅占用 8 字节的内存。 您也许已经注意到,从上一篇文章的结构中删除了一个变量。 原因是我们将不再使用这种锁定方法。 我们将采取一种不同的方式,稍微复杂一些,但对于把控制指标限定于单个图表方面则有效得多。 这将是一个非常具体和明确的回放服务。
1 Z& q3 U( H3 t1 z4 U7 B4 `注意: 如果 MetaTrader 5 平台和 MQL5 语言的开发人员为该服务提供了向特定图表添加指标的能力,或者允许该服务在图表上调用和执行脚本,那将会很有趣。 使用脚本,我们可以将指标添加到特定图表当中,但目前服务无法做到这一点。我们可以打开图表,但不能向其内添加指标。 当尝试执行此动作时,即使我们使用 MQL5 函数,也始终显示错误消息。 在撰写本文时,MetaTrader 5 版本为 build 3280。& p1 e$ B7 R4 t8 M" n& d
重要提示:在撰写本章的这个阶段,这是一个更高级的阶段,由此我才能够实现这一点。 不过,当我撰写这篇文章时,我找不到任何可以帮助解决这个问题的参考资料。 因此,请关注这个回放/模拟系列,看看我是如何想出解决方案的。; g/ A+ }  Q& T+ J
在这种关联境况下,通过运行下面的脚本,我们就能够打开指标,并将其添加到图表之中:
/ J8 s" F6 ^6 m. w2 u) I6 n7 w8 [//+------------------------------------------------------------------+
) B1 c2 z/ g& D//| Script program start function                                    |2 v/ [/ B" r  @3 f
//+------------------------------------------------------------------+
  D9 K/ s- N) o: ?- a5 R( N. svoid OnStart()
8 s8 a2 @9 J! ?, |{
0 U/ |0 A3 i. N- iENUM_TIMEFRAMES time = PERIOD_D1;8 T$ p* K; e7 p0 f; Z7 {6 g6 I5 C
string szSymbol = "EURUSD";
% a) r5 d  p* s4 ^: @  p6 Xlong id = ChartOpen(szSymbol, time);8 O' w, F/ e% Z4 q5 [+ G# ?
ChartRedraw(id);
3 H$ X& X! I+ ^/ h, U( V4 p/ d( A' YChartIndicatorAdd(id, 0, iCustom(szSymbol, time, "Media Movel.ex5"));' S4 ~0 b0 q# z( [3 ]" \% V& h
}& C* E  [; N$ C8 k
然而,如果我们将相同的脚本转换为服务,我们就不会得到相同的结果。
http://www.simu001.cn/x288003x1x1.html
最好的私募社区 | 第一私募论坛 | http://www.simu001.cn

精彩推荐

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|Archiver| ( 桂ICP备12001440号-3 )|网站地图

GMT+8, 2024-5-20 09:01 , Processed in 0.353974 second(s), 31 queries .

Powered by www.simu001.cn X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表