記事"DLLを使用せず、名前のつけられたパイプを使っての MetaTrader 5との通信"についてのディスカッション - ページ 4

 
Renat:
文字列を送信する場合、そのサイズの4バイトを先に送信するようにした。

明示的にバッファサイズを指定してデータを受信する機能を修正した。

逆転送がうまくいかなかった原因、転送データの長さを指定していなかったことがわかった。

ありがとうございました。すべてうまくいきました。

パイプは強力だ。この記事の著者に敬意を表します。

 
Renat:
それはMetaTrader 4の最後のビルドで行われました。
申し訳ありません、何か見落としていたようです。アナウンス445を見ましたが、確かにそこにはpipsについて書かれています。問題はヘルプにそれについての記述がないことです。この件に関するアップデートはいつあるのでしょうか? フォーラムで説明していただけると助かります。
 

4のパイプは5と同様に、ファイル操作でも機能する。

MT4用の記事をリリースする予定です。

 
Renat:

4のパイプは5と同様に、ファイル操作でも機能する。

MT4用の記事をリリースする予定です。

こんにちは、MT4の簡単な例を教えてください。 もちろん、記事を期待しているわけではありません。

具体的には、自分で書いたプログラムから3つのパラメータをターミナルのExpert Advisorに読み込む方法に興味があります。

 
Renat:
MetaTrader 4の最後のビルドで作成されました。

MT5ではすべて正常に動作しているようです。

唯一のポイントは

  • ReadStringや その他のメソッドを使用してチャネルから読み込もうと するときに、パイプチャネルの整合性が最初にチェックされるようにするとよいでしょう。

そうでないと、サーバー側が長時間クローズしているにもかかわらず、WaitForRead メソッドで無期限にハングします。これはすべてWin7-64で チェックした。

サーバー側のWaitForRead メソッドにタイムアウトと他のトリックを追加して、チャネルの両側で自動再接続するシステムを動作させた、

しかし、ちょっと "カクカク "している。

 
Dima_S:

MT5ではすべてうまくいっているようです。

唯一のポイントは

  • ReadStringや その他のメソッドを使ってチャネルから読み込もうと するときに、まずパイプチャネルの整合性がチェックされるようにするとよいでしょう。

そうでないと、サーバー側が長時間クローズしているにもかかわらず、WaitForRead メソッドで無期限にハングします。これはすべてWin7-64で チェックした。

サーバー側のWaitForRead メソッドにタイムアウトやその他のトリックを追加して、チャネルの両側で自動再接続ができるようにした、

しかし、ちょっと "松葉づえ "のようなものだ。

私たちの側からは、その可能性を示すことができました。

あなたのクラスのバリエーションを投稿してください。私たちは標準クラスを最終決定します。

 
実際には、WaitForRead メソッドだけを追加し、エラーチェックとタイムアウト(待ち時間-従来の単位では約20ミリ秒間隔)で終了するようにした:
bool
CFilePipe::WaitForRead( const ulong size, const int _time_out )
{
  int  count = 0;

  while( count < _time_out && m_handle != INVALID_HANDLE && !IsStopped( ))
  {
    if( FileSize( m_handle ) >= size )
    {
     return( true );
    }
    else if( GetLastError( ) != 0 )
    {
      return( false );
    }
    Sleep( 1 );
    count++;
  }

  return( false );
}


クライアント部分は大体こんな感じ:

while( !IsStopped( ))
{
// サーバーへの接続を試みる:
  Print( "Try to connect" );
  if( pipe_Ptr.Open( ch_name, FILE_READ | FILE_WRITE | FILE_ANSI ) != INVALID_HANDLE )
  {
    if( IsStopped( ))
    {
      pipe_Ptr.Close( );
      return;
    }
    Print( "Pipe " + ch_name + " opened" );

// データ受信サイクル:
    while( !IsStopped( ))
    {
// 接続の完全性をチェックする:
      if( !pipe_Ptr.WriteString( "@" ))
      {
        Print( "Disconnected: ", GetLastError( ));
        pipe_Ptr.Close( );
        break;
      }

// データを取得する:
      if( pipe_Ptr.WaitForRead( sizeof( int ), 100 ))
      {
        if( !pipe_Ptr.ReadString( str ))
        {
          Print( "Reading string failed: ", GetLastError( ));
          pipe_Ptr.Close( );
          break;
        }
        Print( "Server: ", str, " received" );
      }
    }
  }
  Sleep( 1000 );
}

ポイントは、データの到着を待っている間に使われるFileSize メソッドが、コネクション違反を検出しない(チェックしないらしい)ことだ。

タイムアウトは役に立ちますが、IMHOはすべての可能な状況においてではありません。FileSize メソッドでこれらのエラーをすべてチェックするのは良いことだと思います。

 

奇妙なことに...。

alt+PrntScrを使ってエディタに貼り付けると、画像は挿入されるが、メッセージはブランチに入らない。

さて、問題は記事のテスト例が通らないことです。

しかしターミナルでは、スクリプトをチャートから削除するまで何もログに残りません。

ログを見ると

2013.03.26 15:33:11     PipeClient (EURUSD,M5)  Client: sending welcome message failed
2013.03.26 15:33:11     PipeClient (EURUSD,M5)  Client: pipe opened

Win7x64 ビルド 787 2013年3月21日

 

確認したところ、すべてうまくいった。


MQ5では、次の行を置き換えるだけです。

uint items=ExtPipe.ReadDoubleArray(buffer);

на 

uint items=ExtPipe.ReadArray(buffer);
 
Renat:

確認したところ、すべてうまくいった。


MQ5ではラインを交換するだけです。

私は持っていない...

その行を置き換えないとコンパイルできないんだ。