四目观天下

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

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

[复制链接]
发表于 2024-4-4 08:08:25 | 显示全部楼层 |阅读模式
概述2 T% h! E% L- M3 ?5 }
在上一篇文章我们曾做过一些修正和调整。 不过,依旧还有错误,如该文所附的视频所示。+ X8 m. v; M% Y9 c( z
在本文中,我们将亲眼见证如何修复此错误。 虽然表面上看这似乎很简单,但我们需要遵循若干个步骤。 这个过程将是奇妙和有趣的。 我们的目标是令指标专门应用于特定的图表和品种。 即使用户尝试,他们也无法将指标应用于另外的图表,或在一个会话中多次打开它。
6 x6 `0 t& J1 f我鼓励您继续阅读,因为内容承诺非常实用。/ I  x- N* O8 v: X2 [
将指标锁定在特定品种上。0 M' y& @0 @/ v* r- U" y  q
第一步是将控制指标链接到进行市场回放的品种。 这一步虽然看起来很简单,但对于开发我们的主要任务是必要的。 我们来看看指标代码在上下文中会是什么样子:- h. `) b- S6 i; I/ z
#property copyright "Daniel Jose"
& o4 ^% c7 N8 R#property indicator_chart_window0 T4 e3 G7 a- }5 P% O9 v) C
#property indicator_plots 0, A7 t. Q1 y' \5 V7 i
//+------------------------------------------------------------------+: \" f# M9 m+ v2 j- `
#include <Market Replay\C_Controls.mqh>: [( T9 }/ A7 P
//+------------------------------------------------------------------+
7 E' Q: c2 X, h6 \C_Controls      Control;. S& r" \5 X# S
//+------------------------------------------------------------------+: M9 P4 j0 @5 T' Z* i
int OnInit(): M7 H* l! N6 r# g  U# ]- }
{
- g$ ~7 k3 V% S$ \. m& i3 Gu_Interprocess Info;
0 R8 \6 u% K) v6 ~6 _% f6 _. U% e/ AIndicatorSetString(INDICATOR_SHORTNAME, def_ShortName);' j: A: Q( |: x+ S! s9 w
if (_Symbol != def_SymbolReplay)
# a' ~9 l* l  A- d4 f0 ?{
( v$ a% w' ]& F" F, v7 Q7 {ChartIndicatorDelete(ChartID(), 0, def_ShortName);* M! n; Y4 r( o& a
return INIT_FAILED;
) Z5 O5 Q# k& W1 o: t# a. \}; K& [$ ?$ q8 j7 q1 r5 o1 @
if (GlobalVariableCheck(def_GlobalVariableReplay)) Info.Value = GlobalVariableGet(def_GlobalVariableReplay); else Info.Value = 0;
' S5 l0 b. x: s7 @Control.Init(Info.s_Infos.isPlay);) r/ U7 u. O: h6 f' P& a& O% \1 h
return INIT_SUCCEEDED;
) Y+ C' r2 |- g" c6 d; O2 c}3 r( k# r* a/ V* {/ `
//+------------------------------------------------------------------+0 E2 d) Q. q3 U
int OnCalculate(const int rates_total, const int prev_calculated, const int begin, const double &price[])) `2 E9 W6 |5 ], |: f/ T" R* A
{0 p7 G; G' `' j
return rates_total;9 O( k" Y; w/ r# h/ s/ [
}. b% ]6 P  B3 w6 w; X3 w
//+------------------------------------------------------------------+
  N' A3 [8 S5 `% v, Dvoid OnChartEvent(const int id, const long &lparam, const double &dparam, const string &sparam)
" P- \1 z8 f5 N7 V" }{- Y" W5 I$ A- ]9 ^+ q! b
Control.DispatchMessage(id, lparam, dparam, sparam);
- R1 J0 |: m% J# |0 x}8 ]5 }7 c7 b7 h# M: [1 x  C7 S
//+------------------------------------------------------------------+
! V2 _- c9 U' Q0 S  Z' Cvoid OnDeinit(const int reason)
) [6 a& C; x: W2 s; i$ q* `+ r{
" n4 f9 j" |0 \1 B/ p3 O  }( iswitch (reason)
8 I6 `4 X! B" X( _{
5 R- X' z: Z( o5 |case REASON_REMOVE:
+ N4 V* z9 o5 g+ o2 H$ h- q! [case REASON_CHARTCLOSE:& a# a3 r1 c8 Q, |& F. G. Z2 m
if (_Symbol != def_SymbolReplay) break;& E7 D8 J* s2 R
GlobalVariableDel(def_GlobalVariableReplay);
8 P# m7 \4 C5 DChartClose(ChartID());
, G9 V: g4 M/ n6 ?" _4 Obreak;9 w- X% T$ O% l0 ]
}, X' q- `5 ]4 p/ A
}
* @3 `9 R6 N. @0 J1 ^( j" P//+------------------------------------------------------------------+
$ \  R! `8 ?6 y, l6 V' y/ t# f我们首先检查针对的品种是否要进行市场回放。 如果不是这种情况,指标将自动关闭。 请注意,知道指标的名称很重要。 因此,初始化期间执行的第一个函数调用我们的指标,这令我们能够轻松删除它。( @6 t. a0 Z, C, G' G
现在重要的一点是:当您将其从图表中删除时,MetaTrader 5 会生成 DeInit 事件。 此事件触发 OnDeInit 函数,而标记为 REASON_REMOVE 的事件表示从图表中删除指标。 这是因为该品种与指标设计绑定的品种不同。 如果我们不重新检查并阻止代码运行,品种图表将关闭。 不过,幸亏我们的检查,它将保持开放状态。- c. s1 z9 y& z& x4 h4 x1 M* A, ?( Y. @
如果指标代码与上一篇文章中提供的代码不同,请不要感到惊讶:上一篇文章重点在于其它改进和修复。 不过,在编写了文章和代码,并录制了本文随附的视频后,我意识到尽管其中一个问题已解决,但另一个问题仍未被发现。 这就是为什么我不得不修改代码。1 n- F0 A( ?2 |+ S( D7 w
尽管进行了修改,但我们不会在此处详述所做的全部修改。 必须删除很大一部分,因为它对于此处讨论的锁定方面无效。 因此,上面的代码与以前的代码有很大差别。 不过,我相信上一篇文章中讲演的知识在某些时候可能对某些人有用。 我保存了那篇文章,以表明有时我们都会犯错误,但我们依旧应该努力把事情做好。
2 t' G0 }4 g0 g8 p因此,我们来建立第一个锁定步骤,即确保控制指标仅存在于市场回放品种的图表上。 然而,该衡量值并不会阻止向同一图表或不同图表添加多个指标,因此必须进行调整。
* s/ \* c: C  Q# o0 j我们应该避免在同一图表上多次使用指标。
/ u  B, f) B2 N4 x9 `我们已经解决了一个问题,现在我们来应对另一个问题。 这里有各种解决方案,这取决于我们真正想要和愿意做什么。 就个人而言,我没有看到这个问题的理想和最终解决方案。 不过,我将尝试提出一种方式,读者能感到熟悉和理解。 最重要的是,该解决方案将完全基于 MQL5。 我甚至考虑过使用外部编码的可能性,但最终决定使用纯 MQL5。 诉诸外部编码,并利用 DLL 进行锁定的想法很诱人,但这太容易了。' v. q) \$ M* ]# V
我认为在诉诸外部 DLL 来填补 MQL5 语言无法胜任的空白之前,我们在 MQL5 中还有很多东西需要学习。 这将提供一个在使用外部代码时看起来“更干净”的解决方案。 只是,这并无助于更好地理解 MQL5。 此外,这可能会强化 MetaTrader 5 是一个受限平台的误解。 对平台的误解和效力利用不足助长了这种误解。" i% K# S( e& M$ T; ~' a& a. X! ]) ]
为了应用我们提议的解决方案,您不得不进行一些修改,并撤回其它更改。 第一步是更改 InterProcess.mqh 头文件,令其拥有以下结构:- a/ j. X# e. C5 j
#property copyright "Daniel Jose"
6 B; z; f3 Z0 N/ e% @/ c/ u//+------------------------------------------------------------------+3 }8 n5 p+ T( w4 F5 S
#define def_GlobalVariableReplay        "Replay Infos"8 ]% Q. ~. j, t# z; N5 P
#define def_GlobalVariableIdGraphics    "Replay ID"$ w0 |/ E4 |; D3 K/ C% O
#define def_SymbolReplay                "RePlay"
( j) [! Q/ X' b5 e: b4 d#define def_MaxPosSlider                4009 l: f3 O' a- X0 V' ]3 F* g# u
#define def_ShortName                   "Market Replay"
* C5 C& W' f: E- O" W4 Z. D//+------------------------------------------------------------------+
- d3 y, Q" w6 @5 w8 ~( K" kunion u_Interprocess% z/ N+ i3 X8 C8 [1 y' N2 l
{
" ?4 Y6 S9 T' R$ c5 w4 R. hunion u_0
! K% W6 h. G: I( D! U{( m( e4 Q# Y. @8 I
double  df_Value;
; C9 W+ t  ^% }3 p( Q+ S! Tlong    IdGraphic;
6 Z4 l* u7 \% c* m) P; C}u_Value;. L# ?# b3 H7 Y+ F& Y
struct st_0; Z& p# C$ J  L4 c; e3 u
{5 j$ {( J. @' ?/ o, R/ Q
bool    isPlay;2 j, y) z+ I4 X+ Y8 q; |, l) D
int     iPosShift;) V. y1 I$ S5 i/ j
}s_Infos;9 p. ~, c& n6 R1 V& Q
};# D" x7 W! z) R, q4 E" A% k
//+------------------------------------------------------------------+" z' {7 E0 h* m2 c. R
对于许多不熟悉编程的人来说,这似乎有点奇怪,但令人惊讶的是,上述结构仅占用 8 字节的内存。 您也许已经注意到,从上一篇文章的结构中删除了一个变量。 原因是我们将不再使用这种锁定方法。 我们将采取一种不同的方式,稍微复杂一些,但对于把控制指标限定于单个图表方面则有效得多。 这将是一个非常具体和明确的回放服务。% {0 U, p6 K# t1 Q/ x
注意: 如果 MetaTrader 5 平台和 MQL5 语言的开发人员为该服务提供了向特定图表添加指标的能力,或者允许该服务在图表上调用和执行脚本,那将会很有趣。 使用脚本,我们可以将指标添加到特定图表当中,但目前服务无法做到这一点。我们可以打开图表,但不能向其内添加指标。 当尝试执行此动作时,即使我们使用 MQL5 函数,也始终显示错误消息。 在撰写本文时,MetaTrader 5 版本为 build 3280。
0 x5 p8 U3 O$ v3 n1 M6 C重要提示:在撰写本章的这个阶段,这是一个更高级的阶段,由此我才能够实现这一点。 不过,当我撰写这篇文章时,我找不到任何可以帮助解决这个问题的参考资料。 因此,请关注这个回放/模拟系列,看看我是如何想出解决方案的。2 c1 X3 c" X% E6 f: R0 ], u
在这种关联境况下,通过运行下面的脚本,我们就能够打开指标,并将其添加到图表之中:
/ C5 s& {& R) [//+------------------------------------------------------------------+( s' n9 y9 r) L! i
//| Script program start function                                    |
9 Z* q) L/ z) Y( \9 I$ W//+------------------------------------------------------------------+' T; t+ o- s* D  K& p5 K0 a1 Q" ], B
void OnStart()% D* j6 b, \. J) `$ I& }  P6 j5 _
{
8 |: \$ d) J6 l% M3 A' C  L3 d5 AENUM_TIMEFRAMES time = PERIOD_D1;
# a+ e* N1 C$ R% W4 _9 qstring szSymbol = "EURUSD";
! c. q/ C7 s. Y9 S( zlong id = ChartOpen(szSymbol, time);
5 f1 G) F$ y9 U8 `+ I0 N0 BChartRedraw(id);% i/ M: E5 E3 w0 I
ChartIndicatorAdd(id, 0, iCustom(szSymbol, time, "Media Movel.ex5"));
& ]5 O' I. Z8 h4 G: e. B5 J}
; e; p6 i4 {$ I. c  W" \( ^然而,如果我们将相同的脚本转换为服务,我们就不会得到相同的结果。
http://www.simu001.cn/x288003x1x1.html
最好的私募社区 | 第一私募论坛 | http://www.simu001.cn

精彩推荐

回复

使用道具 举报

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

本版积分规则

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

GMT+8, 2026-7-30 18:14 , Processed in 1.186058 second(s), 31 queries .

Powered by www.simu001.cn X3.4

Copyright © 2001-2021, Tencent Cloud.

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