MQL4、MQL5に関する初心者からの質問、アルゴリズムやコードに関するヘルプ、ディスカッションなど。 - ページ 624

 
Galim_V:

を修正する方法です。

には、コードに 多くの誤りが あります。

if(OrderModify(OrderTicket(),OrderOpenPrice(),StopLoss_SELL,0,0,Green))

価格を正規化した方が良い、そうすれば動作する、そうすればサーバーは「価格が間違っている」というエラーを出す、StopLoss_SELLを 正規化することが望ましい。

で、ほとんどの場合、StopLossが0に等しいかどうかを確認する必要があり、実数を比較して等しくなることは望ましくなく、実数を比較して>または<になるようにする必要があります。

 
Jessy111:

このインジケーターのバグを修正するのを手伝ってください。

私はインジケーターをスケッチしました。あなたのコードは文字列を扱うのが好きではないので、私ならもっとシンプルに書きますね。ただし、サーバーの時間 オフセットを考慮する必要がある場合は、その逆が必要です。

#property copyright "Copyright 2018, MetaQuotes Software Corp."
#property link      "https://www.mql5.com/ru/users/igorm"
#property version   "1.00"
#property strict
#property indicator_chart_window
#property indicator_buffers 2
#property indicator_plots   2
//--- plot line1
#property indicator_label1  "HighDay"
#property indicator_type1   DRAW_LINE
#property indicator_color1  clrRed
#property indicator_style1  STYLE_SOLID
#property indicator_width1  1

#property indicator_label2  "LowDay"
#property indicator_type2   DRAW_LINE
#property indicator_color2  clrBlue
#property indicator_style2  STYLE_SOLID
#property indicator_width2  1

static int LastDay=-1,daystart;
static double dhigh,dlow;
//--- indicator buffers
double         H[],L[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- indicator buffers mapping
   SetIndexBuffer(0,H);
   SetIndexBuffer(1,L);
   IndicatorDigits(_Digits);
   LastDay=-1;
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
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[])
  {
//---
   int i,j,limit;
   if(prev_calculated==0)
     {
      limit=rates_total-1;
      LastDay=-1;
      daystart=limit;
      dhigh = high[limit];
      dlow  = low[limit];
// расчет истории      
      for(i=limit; i>=0 && !IsStopped(); i--)
        {
         if(LastDay!=TimeDay(time[i]))
           {
            LastDay=TimeDay(time[i]);
            j=daystart;
            daystart=i;
            while(j>daystart)
              {
               H[j]=dhigh;
               L[j]=dlow;
               j--;
              }
            dhigh = high[i];
            dlow  = low[i];
           }
         dhigh= fmax(dhigh,high[i]);
         dlow =  fmin(dlow,low[i]);
        }
// рисуем текущий день при первом запуске
      i=daystart;
      while(i>=0)
        {
         H[i]=dhigh;
         L[i]=dlow;
         i--;
        }
     }
   else
     {
// рисуем текущий день на каждом тике
      i=0;
      dhigh = high[0];
      dlow  = low[0];
      while(TimeDay(time[0])==TimeDay(time[i]))
        {
         dhigh= fmax(dhigh,high[i]);
         dlow =  fmin(dlow,low[i]);
         i++;
        }
      while(i>=0)
        {
         H[i]=dhigh;
         L[i]=dlow;
         i--;
        }
     }
//---
   return(rates_total);
  }
//+------------------------------------------------------------------+

私の例も例ではなく、速く書いたのですが、最初の実行時に履歴の終わりから始まりまで数えるのではなく、ゼロバーから履歴まで数えるようにすれば、コードが短くなり、より速く現在の日を計算することができたはずです - サイクルが短くなったはずです。

でも、テスターで確認したところ、問題なく動くようです、そういうことにしておいてください、もう遅いので、眠いです・・・。悪い例を作ってしまった((

 
Igor Makanu:

には、コードに多くの誤りが あります。

価格を正規化した方が良い、そうすれば動作する、そうすればサーバーは「価格が間違っている」というエラーを出す、StopLoss_SELLを 正規化することが望ましい。

また、ほとんどの場合、StopLossが0に等しいかどうかをチェックする必要がありますが、実数を比較して等しくなることは望ましくなく、実数を比較して>または<になるようにする必要があります。

そうなんです。マーケットからのストップ注文をリクエストすると0になる、という理由です。

 
Igor Makanu:

これはインジケータのスケッチですが、私はあなたの文字列を使ったコードが好きではありません、私ならもっとシンプルに書きます。ただし、サーバーのタイムオフセットを考慮するのであれば、別の方法をとる必要があります。

私の例も例ではなく、速く書いたのですが、最初の実行時に履歴の終わりから始まりまで数えるのではなく、ゼロバーから履歴まで数えるようにすれば、コードが短くなり、より速く現在の日を計算することができたはずです - サイクルが短くなったはずです。

でも、テスターで確認したところ、問題なく動くようです、そういうことにしておいてください、もう遅いので、眠いです・・・。悪い例ができた((

私のコードではなく、インターネットで見つけたもので、インジケータは書けません。:)

悪い例ですが、私はあなたのインディケータが本当に好きで、ストラテジーテスターでも実際のチャートでも機能します。

迅速な対応に感謝します。

また、チャンネルを描く線を削除していただいてもよろしいでしょうか。 スクリーンショットで赤い矢印でマークしています。

あと、全然面倒でなければ、現在日でのセリフの形成のOFF/ONの機能を追加してください。スクリーンショットに青い矢印で印をつけました。https://prnt.sc/kuuj3e。

ありがとうございました。

Скриншот
Скриншот
  • prnt.sc
Снято с помощью Lightshot
 

ハローディア!

OnInit()プロシージャの実行方法を教えてください。

Expert Advisorの変数が変更された後!?

Expert Advisor をチャートに配置するときは、OnInit() がありますが、変数を変更すると、OnInit がありません!?

Expert Advisorの変数変更のイベントを識別する方法!?

アドバイスというか、コードで助けてください!どうすればいいんですか?

 
Игорь:

ハローディア!

OnInit()プロシージャの実行方法を教えてください。

Expert Advisorの変数が変更された後!?

Expert Advisor をチャートに配置するときは、OnInit() がありますが、変数を変更すると、OnInit がありません!?

Expert Advisorの変数変更のイベントを識別する方法!?

アドバイスというか、コードで助けてください!どうすればいいんですか?

#property copyright "Copyright 2018, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict

input int var1 = 1;
//+------------------------------------------------------------------+
int OnInit()
  {
      Print("Вызов OnInit(), var1=",var1);
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
void OnDeinit(const int reason){}
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {

  }
//+------------------------------------------------------------------+

このコードで実験し、EAのログのメッセージを読む(TFを切り替える、変数を入力する、EAを閉じずにターミナルを再起動する...)。

と、グローバルスコープの変数にstaticという修飾 子をつけて記述する方法があります。

#property strict

input int var1=1;
static bool FirstRun=true;
//+------------------------------------------------------------------+
int OnInit()
  {
   Print("Вызов OnInit(), var1=",var1);
// раскоментируйте FirstRun=true; если нужно контролировать вызов OnInit()
//   FirstRun=true;     
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
void OnDeinit(const int reason){}
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
   if(FirstRun)
     {
      Print("Это первый запуск эксперта");
      FirstRun=false;
     }
  }
//+------------------------------------------------------------------+
 
Igor Makanu:

このようなコードで実験し、Expert Advisor のログにあるメッセージを読む(TF を切り替える、変数を入力する、Expert Advisor を閉じずにターミナルを再ロードする...)。

と、グローバルスコープの変数に staticという修飾 子をつけて記述する方法があります。

グローバルスコープでモディファイアstaticで? これはある種の倒錯です。

 
Alexey Viktorov:

モディファイの静的な グローバルレベルでは これはある種の倒錯です。

しかし、私の経験では、MT4のビルドが頻繁に更新されたとき、開発者とのコミュニケーションで「コードを正しく書いてください」という答えを得るよりも、クラシックC++に従って書いた 方が良いのです



ZS: なぜstatic修飾子をグローバルに書くようになったか、それはMQLプログラムの実行中に変数の値が「失われない」ようにするためです。 以前(5年ほど前)は#property strictプリコンパイラ指令が存在せず、ファイル(#includeまたはlibrary - もう覚えていません)を有効にすると、変数名が変数名と一致するので「私の変数」を一度失くしました。MQLに呪われていたのですが、後で偶然このミスを発見しました。 しかし、もし私がstatic modifierを書くと、コンパイラはその場合にもコンパイルエラーを表示するのです。

現在のMT4コンパイラはかなり便利で信頼性が高く、#property strictディレクティブを使えば、そんな注意は必要ないのかもしれませんが、変数の「値を失いたくない」ときに習慣としてstaticを書きます。

ZZZY: この修飾子はMQLプログラムの実行速度に影響を与えません。また、後で自分のコードを開いて、この変数が値を持っていることを静的に知ることができるので、プログラム実行中に「失う」ことがないようにするために便利です。

 
Igor Makanu:

しかし、私の経験では、MT4のビルドが頻繁に更新されたとき、開発者とのコミュニケーションで「コードを正しく書いてください」という答えを聞くより、クラシックなC++の 方法で書いた方が良いのです



ZS: なぜstatic修飾子をグローバルに書くようになったか、それはMQLプログラムの実行中に変数の値が「失われない」ようにするためです。 以前(5年ほど前)は#property strictプリコンパイラ指令が存在せず、ファイル(#includeまたはlibrary - もう覚えていません)を有効にすると、変数名が変数名と一致するので「私の変数」を一度失くしました。MQLに呪われていたのですが、後で偶然このミスを発見しました。 しかし、もし私がstatic modifierを書くと、コンパイラはその場合にもコンパイルエラーを表示するのです。

現在のMT4コンパイラはかなり便利で信頼性が高く、#property strictディレクティブを使えば、そんな注意は必要ないのかもしれませんが、変数の「値を失いたくない」ときに習慣としてstaticを書きます。

ZZZY: この修飾子はMQLプログラムの実行速度に影響を与えません。また、しばらくしてから自分のコードを開き、静的変数を見て、この変数には値があることを正確に知ることができ、プログラム実行中に「失わない」ことが重要です。

コンパイラは、変数名がインクルードファイルの変数名と一致する場合、警告を発生させます。私にとっては、警告はエラーに等しいので、同じように反応します。そして、static修飾子を 持つグローバルレベル変数は、オイルに等しい。

でも...そんな風に書くのが好きなら、誰もそれを禁止することはできない。

 
Alexey Viktorov:

でも...でも...こうやって書くのが好きなら、誰もそれを禁止することはできないんだ。

この件に関しては、自分の独自性に疑問がある...。私だけではなく、MQL5のフォルダを検索すると、MT5配信のいくつかのソースコードで、グローバルレベルでstatic修飾子を 使った宣言を見つけることができました。

ソースコードの「RANDOM DECISION FOREST IN THE SUMMARY」の記事でも、static datetime last_time=0 というグローバルレベルでの宣言がありました。

だから私は私が割り当てに合うように書いて、される、私は静的として記述するグローバルレベルでの変数の100%ではありません

神は困窮者を守る、と尼僧は言った... ))))