新人对MQL4和MQL5的任何问题,对算法和代码的帮助和讨论 - 页 808

 
Kos Mos:

所以我试图找出我失败的原因,我明白没有人可能免费告诉我任何事情--资本主义,看在他妈的份上))。我并不反对,我只是需要了解为什么在买入方向的每根蜡烛上都有交易。

我不是在回答你的问题。

如果你想让你的滑雪板工作,你至少要在收到信号时打印出 重要的变量值,并在日志中查看这些变量的情况。

 

有一个循环for(int i=0;i<ArrayRange(arr2,0);i++),所以我想知道这个计算ArrayRange(arr2,0)被执行了多少次:一次,机器记住了这个值,还是每次循环运行时,从ArrayRange(arr2,0)函数 返回这个值?例子。

第一种选择。

i=0,i<(返回值), 递增, 然后

i<(再次返回值),增量,然后

i<(再次返回一个值),这样递增。

第二种变体。

或者,我们从这个计算中返回一个值 ArrayRange(arr2,0)一次,让它返回5,机器记住这个5,得到如下结果

i=0,i<(返回值)i<5, 递增,然后

i<5,增加,然后

i<5,增量--是这样操作的吗?

我在问为什么:如果一切都由第一个变量发生,那么在循环之前提取这个值并将其存储在一个变量中是有意义的,这样程序就不会在每个循环通道上计算ArrayRange(arr2,0)函数。

 
Seric29:

有一个循环for(int i=0;i<ArrayRange(arr2,0);i++),所以我想知道这个计算ArrayRange(arr2,0)被执行了多少次:一次,机器记住了这个值,还是每次循环运行时,从ArrayRange(arr2,0)函数 返回这个值?例子。

第一种选择。

i=0,i<(返回值), 递增, 然后

i<(再次返回值),增量,然后

i<(再次返回一个值),这样递增。

第二种变体。

或者,我们从这个计算中返回一个值 ArrayRange(arr2,0)一次,让它返回5,机器记住这个5,得到如下结果

i=0,i<(返回值)i<5, 递增,然后

i<5,增加,然后

i<5,增量--是这样操作的吗?

我问的原因是:如果所有的事情都发生在第一个变量上,那么在循环之前,首先提取这个值并将其存储在一个变量中是有意义的,这样在循环的每个段落中,程序就不会做出ArrayRange(arr2,0)这个函数。

在一般情况下--第一种情况。

PS/ 只有 "优化 "的编译器才有可能做到这一点,它能够理解如果在一个循环中没有ArrayResize,那么ArrayRange:=const;我不确定mql编译器已经对代码进行了如此深入的挖掘,尽管对于它的 "本地 "函数来说,这在理论上是可能的。

PPS/ ArrayRange()的例子不太正确,因为可能不会有直接的函数调用,编译器只需将其简化为将i与内部数组变量进行比较,因为它知道关于数组的一切。

 
Maxim Kuznetsov:

在一般情况下--第一种变体。

PS/ 第二种情况只有 "优化 "编译器才有可能,它可以理解,如果循环内没有ArrayResize,那么ArrayRange:=const;不确定mql编译器是否已经深入挖掘代码,尽管对于它的 "本地 "函数,理论上是可能的。

PPS/使用ArrayRange()的例子不太正确,因为可能不会有直接的函数调用,编译器只是将其简化为i与内部数组变量的比较,因为它知道关于数组的一切。

让我们来看看5+5*5 的表达方式

第1种变体。

i=0,i<(5+5*5), 递增,然后

i<(5+5*5), 递增, 然后

i<(5+5*5),这样递增。

第二种变体。

或者,在这种情况下,结果是单次返回 5+5*5,让他们返回30,机器会记住这个30区,所以我们得到以下结果

i=0,i<(返回值) i<30, 递增, next (引擎自动记住了30,因为我没有在某个地方保存30)

i<30,增加,然后

i<30,增量,是这样的吗?

我认为这将是第1种变体?5+5*5是一个表达式,将在循环的每一次迭代中被评估。你可以在循环之前计算这个表达式,并将30存储在一个变量中,然后将其送入循环,这样做对机器来说会更容易使用,除非它自动计算这个30并将其存储在内存中。


如果没有函数调用,编译器就不能检查布尔表达式i<5,所以可能第一个选项会有效。

 

一个函数(ArrayRange)的结果可以在一个循环或函数中改变。
而常数表达式(5+5*5) 将永远是相同的。

因此,该函数将在每一次传递中进行计算。
而这个常量值将在编译时被编译器替换到代码中。

 
Taras Slobodyanik:

一个函数(ArrayRange)的结果可以在一个循环或函数中改变。
而常数表达式(5+5*5) 将永远是相同的。

因此,该函数将在每一次传递中进行计算。
而这个常量值将在编译时被编译器替换到代码中。

5+5*5也是一个表达式,它需要在每一次传递中进行计算;至于函数,预计会返回相同的结果;关键是在循环的每一次传递中,编译器仍然会同时计算函数和表达式5+5*5。 所以会采用第一种方案--即在循环的每一次传递中进行计算,所以在循环前计算这个值并将其存储在一个变量中,并将该变量作为同一静态值,以便在循环的每一次传递中不进行计算,这最终使得我的

int k=5+5*5;//k=30

for(int i=0;i<k;i++){}。

其中k总是30或

int k=ArrayRange(arr2,0)//k=5

for(int i=0;i<k;i++){}。

其中k总是等于5。

 
Seric29:

5+5*5也是一个表达式,它需要在每一次传递中进行计算,至于函数,它应该返回相同的结果,我们说的是,在循环的每一次传递中,编译器仍然会计算函数和表达式5+5*5。 所以这将是第一个选项--即在循环的每一次传递中进行计算,所以在循环之前计算这个值并将其存储在一个变量中,将该变量作为相同的静态值,所以在循环的每一次传递中不会有计算,它最终可以

int k=5+5*5;//k=30

for(int i=0;i<k;i++){}。

其中k总是30或

int k=ArrayRange(arr2,0)//k=5

for(int i=0;i<k;i++){}。

其中k总是等于5。

你可以简单地扩展循环,不创建额外的变量。

 
Seric29:

5+5*5也是一个表达式,需要在每一次传递中进行计算,至于函数应该返回相同的结果,我们说的是在循环的每一次传递中,编译器仍然会同时计算函数和表达式5+5*5。 所以会有第一种选择--即在循环的每一次传递中进行计算,所以在循环前计算这个值并存储在一个变量中,将变量作为同一个静态值,这样在循环的每一次传递中没有计算,它最终mo

编译器总是工作一次--在将文本编译成代码的时刻。
(在我的印象中,MT4也已经直接编译为代码了)

5+5*5 - 这是一个带有常数的表达式,它们不需要重新计算 - 所以它只计算一次,在编译时,代码将包含数字30

5+5*5+i是一个带有变量的表达式,这将在每一次的代码中被计算为30+i。

ArrayRange 函数返回一个值,但编译器不知道这个值会是什么,所以它将在代码中替代函数调用,在每一次传递(代码中)函数将被调用
 
Taras Slobodyanik:

编译器总是工作一次--在将文本编译成代码的时刻。
(在我印象中,MT4已经直接编译成代码了)

5+5*5是一个带有常数的表达式,它们不需要重新计算--所以这只需要在编译时计算一次,在代码中它将是30

5+5*5+i是一个带有变量的表达式,它在代码中的每一次计算都是30+i。

ArrayRange 函数返回一个值,但编译器不知道这个值会是什么,所以它将在代码中替代函数调用,在每一次传递(代码中)函数将被调用

我明白了。谢谢你。当然,这不是一个严肃的问题,但也有微妙之处。

 
Artyom Trishkin:

你可以简单地扩展循环,不创建额外的变量。

在我的例子中,有两个数学表达式,第一是ArrayRange(arr2,0),第二是5+5*5,我的目标是创造条件,使编译器在较少的负载下工作

for(int i=0;i<ArrayRange(arr2,0);i++) 在这种情况下,每次都会返回 比较

int k=ArrayRange(arr2,0)//k=5 for(int i=0;i<k;i++){}在这种情况下,比较值被返回1次,而不是4次,但是创建了一个变量,尽管如此,负载还是比较低,特别是当我们谈论的是成千上万或数百万。

你能告诉我们如何扩展一个循环,以便我们不必创建变量吗?

原因: