程序库: Price_Compare

 

Price_Compare:

简单快捷地比较"价格"的双精度值。

作者: fxsaber

 
Automated-Trading:

价格比较

作者:fxsaber

你为什么这么喜欢预处理器指令? 我看到的所有代码中都有预处理器指令。规范化本身是个有趣的话题,但它可以在没有预处理器指令的情况下实现,语言允许你这样做。

按照你的交流风格--举个例子,说明使用你的库会比通常的规范化速度更快:)

 
coderex:

你为什么这么喜欢预处理器指令? 我看到的所有代码中都有。就规范化本身而言,这个话题很有趣,但不需要预处理器指令也能实现,语言允许你这样做。

重复的代码很烦人。我喜欢简洁、高效和逻辑性。例如

关于交易、自动交易系统和交易策略测试的论坛

测试 "CopyTicks

fxsaber, 2016.10.19 07:59

这就是 date-to-date 的作用。CopyTicks仅仅因为名称中含有 "Copy",就试图将语法套入Copy函数,这不会带来任何便利。当你可以像下面这样使用预处理器时,才会觉得方便和合理

// 与 MT4 一样,允许处理时间序列:Open[Pos]、High[Pos]、Low[Pos]、Close[Pos]、Time[Pos]、Volume[Pos]。
// 它还设置了 MT4 的常用功能:iOpen、iHigh、iLow、iClose、iTime、iVolume。
#define DEFINE_TIMESERIE(NAME,FUNC,T)                                                                         \
  class CLASS##NAME                                                                                           \
  {                                                                                                           \
  public:                                                                                                     \
    static T Get( const string Symb, const int TimeFrame, const int iShift )                                  \
    {                                                                                                         \
      T tValue[];                                                                                             \
                                                                                                              \
      return((Copy##FUNC((Symb == NULL) ? _Symbol : Symb, _Period, iShift, 1, tValue) > 0) ? tValue[0] : -1); \
    }                                                                                                         \
                                                                                                              \
    T operator []( const int iPos ) const                                                                     \
    {                                                                                                         \
      return(CLASS##NAME::Get(_Symbol, _Period, iPos));                                                       \
    }                                                                                                         \
  };                                                                                                          \
                                                                                                              \
  CLASS##NAME NAME;                                                                                           \
                                                                                                              \
  T i##NAME( const string Symb, const int TimeFrame, const int iShift )                                       \
  {                                                                                                           \
    return(CLASS##NAME::Get(Symb, TimeFrame, iShift));                                                        \
  }

DEFINE_TIMESERIE(Volume, TickVolume, long)
DEFINE_TIMESERIE(Time, Time, datetime)
DEFINE_TIMESERIE(Open, Open, double)
DEFINE_TIMESERIE(High, High, double)
DEFINE_TIMESERIE(Low, Low, double)
DEFINE_TIMESERIE(Close, Close, double)
而对于 CopyTicks,你不能这样做,因为有两个不同的物理线程(TRADE 和 INFO)和一个合成线程(ALL)--标志。

按照你的交流风格--举例说明使用你的库会显示比正常化更高的速度:)

这主要取决于终端的比特率。在 MT4 上,速度差异应该特别明显。Renat 在此主题中进行了比较。

Альтернативные реализации стандартных функций/подходов
Альтернативные реализации стандартных функций/подходов
  • www.mql5.com
NormalizeDouble Результат 1123275 и 1666643 в пользу MyNormalizeDouble (Optimize=1). Без оптимизации - быстрее раза в четыре (на память...
 
fxsaber:

令人讨厌的重复代码。我喜欢简洁、高效和逻辑性。例如


主要取决于终端的比特率。在 MT4 上,速度上的差异尤其明显。Renat 在此主题中进行了比较。

谢谢 )))),我得到了很多有用的信息
 
coderex:
预处理器实用性的另一个例子

关于交易、自动交易系统和交易策略测试的论坛

初学者的问题

fxsaber, 2016.10.19 15:23

#define ORDER_TYPE_BUY ORDER_TYPE_BUY_STOP   // 如果您想拒绝买入交易,请将其放在 "智能交易系统 "的最开头。
#define ORDER_TYPE_SELL ORDER_TYPE_SELL_STOP // 如果需要拒绝卖出交易,则将其放在 EA 的最开头
 
fxsaber:
预处理器有用性的另一个例子
有时不可能完全拒绝使用预处理器,但你的代码却只是根据预处理器指令编写的。这样的代码会变得难以阅读。
 
coderex:
有时不可能完全拒绝使用预处理器,但你的代码只是根据预处理器指令编写的。这样的代码很难阅读。

我以清晰的方式设置变量、类型、类、函数/方法和宏的名称。如果您发现滥用,请告诉我。

我阅读 kodobase 的最大障碍是强制样式化。我在 kodobase 中的几乎所有代码都经过了这种处理。之后,我几乎无法阅读自己的代码。

 
fxsaber:

变量名、类型名、类名、函数/方法名和宏名的设置都很清晰。如果发现滥用,请告诉我。

我阅读 kodobase 的最大障碍是强制样式化。我在 kodobase 中的几乎所有代码都经过了这种处理。在此之后,我几乎无法阅读自己的代码。

我说的不是我自己,任何充满宏的代码都会被阅读得很糟糕,而且调试起来也非常困难,所以我总是尽量少用预处理器,只有在绝对必要的时候才使用。代码中出现宏表明算法考虑不周,我不记得这些话是谁说的了,应该是斯特劳斯特鲁普,但它们反映了一个本质--代码必须干净。
 
coderex:
我不是在说我自己,任何充满宏的代码都会被阅读得很糟糕,而且调试起来也非常困难,所以我总是尽量少用预处理程序,只有在绝对必要时才使用。代码中出现的宏说明算法考虑不周,我不记得这些话是谁说的了,应该是斯特劳斯特鲁普,但它们反映了一个本质--代码应该是干净的。
我不同意
string GetTickFlag( uint tickflag )
{
  string flag = "";

#define TICKFLAG_MACRO(A) flag += ((bool)(tickflag & TICK_FLAG_##A)) ? " TICK_FLAG_" + #A : "";
  TICKFLAG_MACRO(BID)
  TICKFLAG_MACRO(ASK)
  TICKFLAG_MACRO(LAST)
  TICKFLAG_MACRO(VOLUME)
  TICKFLAG_MACRO(BUY)
  TICKFLAG_MACRO(SELL)
#undef TICKFLAG_MACRO

  if (flag == "")
    flag = " FLAG_UNKNOWN (" + (string)tickflag + ")";
    
  return(flag);
}

#define TOSTRING(A) " " + #A + " = " + (string)Tick.A

string TickToString( const MqlTick &Tick )
{
  return(TOSTRING(time) + "." + (string)IntegerToString(Tick.time_msc %1000, 3, '0') +
         TOSTRING(bid) + TOSTRING(ask) + TOSTRING(last)+ TOSTRING(volume) + GetTickFlag(Tick.flags));
}

void OnStart()
{
  MqlTick Tick;
  
  if (SymbolInfoTick(_Symbol, Tick))
    Print(TickToString(Tick));
}

结果

2016.10.19 18:14:51.604 Test (GBPUSD,M1)         time = 2016.10.19 18:15:58.649 bid = 1.23008 ask = 1.23018 last = 0.0 volume = 0 TICK_FLAG_ASK

我认为它很漂亮。否则,我们也应该放弃模板。

 
fxsaber:
我不同意
string GetTickFlag( uint tickflag )
{
  string flag = "";

#define TICKFLAG_MACRO(A) flag += ((bool)(tickflag & TICK_FLAG_##A)) ? " TICK_FLAG_" + #A : "";
  TICKFLAG_MACRO(BID)
  TICKFLAG_MACRO(ASK)
  TICKFLAG_MACRO(LAST)
  TICKFLAG_MACRO(VOLUME)
  TICKFLAG_MACRO(BUY)
  TICKFLAG_MACRO(SELL)
#undef TICKFLAG_MACRO

  if (flag == "")
    flag = " FLAG_UNKNOWN (" + (string)tickflag + ")";
    
  return(flag);
}

#define TOSTRING(A) " " + #A + " = " + (string)Tick.A

string TickToString( const MqlTick &Tick )
{
  return(TOSTRING(time) + "." + (string)IntegerToString(Tick.time_msc %1000, 3, '0') +
         TOSTRING(bid) + TOSTRING(ask) + TOSTRING(last)+ TOSTRING(volume) + GetTickFlag(Tick.flags));
}

void OnStart()
{
  MqlTick Tick;
  
  if (SymbolInfoTick(_Symbol, Tick))
    Print(TickToString(Tick));
}

结果。

2016.10.19 18:14:51.604 Test (GBPUSD,M1)         time = 2016.10.19 18:15:58.649 bid = 1.23008 ask = 1.23018 last = 0.0 volume = 0 TICK_FLAG_ASK

有点可爱。否则,你也不得不放弃模板。

你喜欢它是可以理解的 )))),但在我看来,TickToString 可以用一种纯粹的语言来实现。

问题的关键在于宏来自于 C 语言,它们是为其他目的而设计的。这就好比微型计算器--创建的目的是一样的,但在那个时代,人们开始玩 MK-62(包括我),但后来由于缺乏 PC 而被迫放弃,现在看起来要么是怀旧加变态,要么就是纯粹的变态:)。宏....当然,您可以按照自己的喜好编写代码,我只是说了吸引您眼球的地方。

 
coderex:
在我看来,TickToString 可以用纯语言实现

当然可以!但会有多难看?

在没有宏的 TypeToBytes 库中,这不仅可怕,而且不方便。也就是说,这个库可以直接扔掉。

我认为这与语言能力有关。当我不知道/不理解 OOP 时,我不会使用它。一切都变了。