記事"トレーダーのライフハック: インジケーターで作られたファストフード"についてのディスカッション - ページ 2

 
Renat Fatkhullin:

...

また、インジケーターから1値だけ抽出するのは非効率的である。

...

これらはすべて理論上の話である。しかし実際には、指標の99%はFIFOリング・バッファで計算される:最後の要素を削除し、新しい要素を追加し、指標を再計算する。つまり、実際にも計算バッファへの追加は1つの要素で行われ、指標の計算の 99%は1つの要素の追加である。従って、CopyBuffer、CopyRates、CopyXXXというアイデアは美しいが、対象分野には対応しない

 
Renat Fatkhullin:

...

ハンドル・リーク(なぜインジケーター・ハンドルを閉じるのか)と驚くべきオーバーヘッド(インジケーターを再作成しようとすると、インジケーター・マネージャーの中に落ちる)を伴うハード・ホラー。そして十分な数の人々が、見もせず理解もせずにそれをコピーする。

...

おっしゃる意味がよくわかりません。私が理解する限り、ハンドルはどこにも閉じられていません(IndicatorReleaseの呼び出しは ありません)。iMACDのようなヘンドル作成の標準的な関数への呼び出しは常にあります:

//+------------------------------------------------------------------+
//| MQL4表記によるiMACD関数|
//| バッファ番号は以下の通り。
//| mql4 0 - mode_main、1 - mode_signal|
| mql5 0 - メイン・ライン、1 - シグナル・ライン|
//+------------------------------------------------------------------+
double   iMACD(
               string                     symbol,              // シンボル名 
               ENUM_TIMEFRAMES            timeframe,           // タイムフレーム 
               int                        fast_ema_period,     // 高速平均の計算期間 
               int                        slow_ema_period,     // スロー平均の計算期間 
               int                        signal_period,       // その差の平均化期間 
               ENUM_APPLIED_PRICE         applied_price,       // 価格またはハンドルの種類 
               int                        buffer,              // バッファ 
               int                        shift                // シフト
               )
  {
   
   double result=NaN;
//---
   int handle=iMACD(symbol,timeframe,fast_ema_period,slow_ema_period,signal_period,applied_price);
   if(handle==INVALID_HANDLE)
     {
      Print(__FUNCTION__,": INVALID_HANDLE error=",GetLastError());
      return(result);
     }
   double val[1];
   int copied=CopyBuffer(handle,buffer,shift,1,val);
   if(copied>0)
      result=val[0];
   else
      Print(__FUNCTION__,": CopyBuffer error=",GetLastError());
   return(result);
  }

明らかに、ここでのゲーム全体は、iMACDや同様の関数が以前に返されたハンドルを自分自身の中にキャッシュするという事実に基づいています。

 
Vasiliy Sokolov:

これはすべて理論上の話だ。しかし実際には、指標の99%はFIFOリング・バッファでの計算である:最後の要素を削除し、新しい要素を追加し、指標を再計算する。つまり、実際にも計算バッファへの追加は1つの要素で行われ、インジケータ内の計算の 99%は1つの要素の追加である。したがって、CopyBuffer、CopyRates、CopyXXXという考え方は美しいが、対象領域には対応しない

最も単純で原始的なラストルックハンドラーを書く場合です。しかし、一歩横にずれて2点以上のチェックを始めると、すぐにその違いと効果がわかる。

もちろん、一般論として、CopyXXX関数は対象外というのはおかしい。

市場環境にアクセスするための基本的な機能について、そのようなことを一生懸命に言うべきです。


また、インジケーターに全履歴の100%が計算のために与えられているのも、無意味なことではない:

int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
これは、「リングバッファの99%」が存在しないことを証明するためである。これは、「リングバッファの99%」が存在しないことを証明するためである。最後の値ではなく、履歴への大量アクセスが非常に必要なのである。
 
Vasiliy Sokolov:

おっしゃる意味がよくわかりません。私が理解する限り、ヘンドルはどこにもクローズされません(IndicatorReleaseへの呼び出しは ありません)。iMACDのような、ヘンドルを作成する標準的な関数が常に呼び出されています:

明らかに、ゲーム全体は、iMACDや同様の関数が、以前に返されたハンドルを自分自身の中にキャッシュするという事実の上に構築されているので、インジケーターの再作成はないはずです。

ゲーム全体が、ハンドルの制御を完全に無視したハックによって成り立っている。

別のトレーダーがこのコードを使用し、ハンドルの割り当てに注意を払わず、異なるパラメータで呼び出しを開始し、インジケータを増殖させ、すべてのハンドルを失い、そしてブレーキとメモリ消費に驚きます。

誰が悪いかは明らかだ。

 
fxsaber:

この記事は別の 記事の一部を抜粋したものだ。

類似点は見当たらない。

fxsaber:

効率的に動作させるために何もしていない。指標や時系列のキャッシュもない。

ここには最適化の余地がある。キャッシュを導入するのは非常に良いアイデアだ。

fxsaber:

High[i]、Low[i]などがありません。

あるべきでしょうか?記事のタイトル(というかその説明)には明らかにインジケータについてのみ書かれていると思うのですが?

fxsaber:

iCustomはありません。

残念ながら、MQLは任意の数のパラメータを持つ関数をサポートしていないため、iCustomを "MT4と同じように "実装することはできません。

fxsaber:

全く違うものが出てくると思っていた。しかも、EAのファーストフードなんて、どうせソースの匂いもしないのに、何の意味があるのでしょうか?

MT4のスタイルを完全にエミュレートした本格的なエンジンを1つの記事で書くことは不可能だと思う。トピックは、MQL4スタイルでインジケータを操作すること、と明記されています(記事のタイトルがトピックを反映しておらず、紛らわしいのが残念です)。

 
Renat Fatkhullin:

...

これは、"リングバッファの99%"が存在しないことを証明するためである。非常に必要とされているのは、履歴への大量アクセスであり、単一の最後の値ではない。

それがあり、常時というより少し頻繁に使われている。ただ、特別な手段がなく、開発者は入れ子のループを作らなければならない。二重にネストされたforを持つインジケータを開いてみてください。MFIインジケータの 超効率的な計算の 例です:

//+------------------------------------------------------------------+
//| 引数から体積でMFIを計算する。
//+------------------------------------------------------------------+
void CalculateMFI(const int nPosition,
                  const int nRatesCount,
                  const double &HiBuffer[],
                  const double &LoBuffer[],
                  const double &ClBuffer[],
                  const long &VolBuffer[],
                  const datetime &time[])
  {
   for(int i=nPosition;i<nRatesCount && !IsStopped();i++)
     {
      double dPositiveMF=0.0;
      double dNegativeMF=0.0;
      double dCurrentTP=TypicalPrice(HiBuffer[i],LoBuffer[i],ClBuffer[i]);
      if(time[i] == D'2016.05.23')
         int dbg = 4;
      for(int j=1;j<=ExtMFIPeriod;j++)
        {
         int    index=i-j;
         double dPreviousTP=TypicalPrice(HiBuffer[index],LoBuffer[index],ClBuffer[index]);
         if(dCurrentTP>dPreviousTP)
            dPositiveMF+=VolBuffer[index+1]*dCurrentTP;
         if(dCurrentTP<dPreviousTP)
            dNegativeMF+=VolBuffer[index+1]*dCurrentTP;
         dCurrentTP = dPreviousTP;
        }
      if(dNegativeMF!=0.0) ExtMFIBuffer[i]=100.0-100.0/(1+dPositiveMF/dNegativeMF);
      else                 ExtMFIBuffer[i]=100.0;
     }
  }

このインジケータの計算速度が平均化期間に依存していることは明らかで、そうであってはなりません。そして、このような例はたくさんあり、その中にはMQ自身が書いたものもあるのですが、あなたはリング・バッファはないと言っています。

 
Vasiliy Sokolov:

それはあるし、いつもというより少し頻繁に使われている。ただ、特別なツールがなく、開発者はネストされたループを作成しなければならない。二重にネストされたforを持つインジケーターを開いてみてください。MFIインジケータの 超効率的な計算の 例です:

このインジケータの計算速度が平均化期間に依存していることは明らかで、そうであってはなりません。そして、このような例はたくさんあり、その中にはMQ自身が書いたものもあります。

リングバッファは99%のケースで存在しません。そして90%のケースでリング・バッファは存在せず、50%のケースでリング・バッファは存在しない。しかし、OnCalculateパラメータには100%の初期データ(歴史の深さ全体)があります。

また、指標を計算することが目的ではなく、指標の結果とソースデータへのアクセスの両方を使用することが目的である。アクセスは1つではなく、大規模に必要です。

あなたは「分析市場全体が最後の指標値で表される」「コピーXXXXは対象分野に対応しない」というような状況を提示しようとしている。

一生懸命スケッチしている。

 
Renat Fatkhullin:

...

そして、それは指標を計算するという問題ですらなく、指標の結果と元のデータへのアクセスの両方を使用するという問題である。アクセスは1つではなく、大規模なものが必要なのだ。

...

リクエスト#1923700に注目してください。大量のデータに頻繁にアクセスすることには問題があります。

この結果の原因を解明するための追加的な意見を提供するためのコメントや質問が久しぶりにありました。

 
Renat Fatkhullin:

別のトレーダーがこのコードを取り、ハンドルの割り当てに注意を払わず、異なるパラメー タでコールを開始し、インジケータを乗算し、すべてのハンドルを失い、ブレーキとメモリ消費に 驚く。

同様に、この別のトレーダーは、標準の iHandles を異なるパラメータで呼び出すことができます。パラメータが異なれば、ハンドルを直接操作しようがMQL4-Styleを使おうが、異なるインジケーターが作成されます。

 
Renat Fatkhullin:

あなたは一生懸命スケッチしようとしている。

そしてこれは残念なことだ。

しかも、指標を計算することではなく、指標の結果として使うことなのに。

そうだね。

レナト・ファトフーリン

...

とにかく、無意味なので議論はしない。コピー***関数の使用に関する統計を取るのは面白いだろう。ユーザーが平均してどれだけのアイテムをコピーしているのかがよくわかるだろう。