English Русский 中文 Español Deutsch Português
MetaTrader 4 クライアントターミナルと MS SQL  Server の統合

MetaTrader 4 クライアントターミナルと MS SQL Server の統合

MetaTrader 4 | 21 4月 2016, 14:06
1 174 0
Yuriy Zaytsev
Yuriy Zaytsev

はじめに

別の製品との統合を行うことで、トレーディングにおいて付加的な挑戦が可能となります。

それには多くの用途があるので、以下にそのうちのいくつかを提示します。

ティックを収集し、それをさらに分析するため MS SQL SERVER に渡します。大きなティック履歴を取得することで、最小の時間単位から開始し非標準的な期間まで任意の期間を収集することができます。実ティックのクオートを取得することで、「スキャルパ」として知られるティックデータ依存の戦略をデバッグすることができます。

別アプリケーションから取り入れられたデータを素早く分析するためにストアをしようすることができます。たとえば、マイクロソフトエクセルや別の第三者ソフトウェア、または自分自身のプロダクトからのデータです。

たとえば、ターミナルの「ヒストリーセンター」から MS SQL に全履歴をアンロードすることが可能です。そして MT4 にその履歴を格納する必要はありません。これはターミナルメモリへの負荷を軽減するのに役立ちます。

MS SQL SERVER に格納されたクオートを利用してニューラルネットワークを計算することができます。たとえば、ネットワーク信号を MT4 に渡すことでリアルタイムモードで STATISTICA - 7.8 により SQL からクオートをダウンロードすることができるのです。

別言語で別シンボルに対する独自のプログラムを作成することができ、サーバーを使ってシグナルを渡すことができます。あとはクライアントターミナルに対する関数を実行するだけで、重い計算の負荷を軽減できるのです。


本プロジェクトには以下のソフトウェア製品が使用されました。

  • MS SQL SERVER 2000 Developer - BASE
  • VISUAL C++ 6.0 SP5 -DLL "YZMSSQLExpertSample.dll" を作成するため
  • MDAC 7


インストールするのは最小セットです。

1 MS SQL SERVER 2000 Developer
2 MDAC 7

私は MDAC によってプログラムをデバッグしました。ただし、古いバージョンの一部ですべて正常に動作する可能性があります。DLL をコンパイルするつもりがなければ、Visual C++ 6.0 をインストールする必要や、インストール済みを取得する必要はありません。既製の DLL を使用することができます。ですが、私はそこにユーザー名、DSN 名、接続をハード配線しました。みなさんは自分バージョンのプログラムに上記リストアップされたものをすべて繰り返す必要があります。ここでMS SQL SERVER や Visual C++ 6.0のインストール方法を説明しません。そういった事柄はこの特定の記事の範囲外であります。

必要なソフトウェア製品がインストールされたら、DSN を作成します。

dsn=MT4_SQL_BASE;", "yuraz", "qwerty"


MS SQL でのティック受け取り例

実験はすべて MS SQL SERVER 2000 Developer によって行われました。Visual C++ 6.0 では、ADO を介して MS SQL にアクセスする方法で YZMSSQLExpertSample.DLL が作成されました。MDAC 7 または MDAC 8 をインストールする必要があります。プロシージャおよびテーブルの作成方法例についてのみ説明します。MS SQL で作成するものの最小セットはべース、テーブル、プロシージャです。ティッククオートを処理するテーブルとプロシージャを考察します。ご希望なら他に関数を追加することも可能です。


ベースとテーブルは MS SQL で作成する必要があります。私は MT4TRADE という名前で新しいベースを作成しました。そしてその中にテーブルを作成します。

MT4TICK -ティックテーブル


//-----------------------------------------------------------------------------------
//
//  Structure of MT4TICK Base
//
//    idc             - formed automatically, unique number of record
//    ServerDateTime  - Filled out automatically, when adding a record
//                        Server local time - time when the quote was placed in the table 
//                        (it doesn't have anything in common with the date and time passed by MT4)
//                        it is the time counted by the server itself - it will be the same as the time
//                        of the machine, on which the server has been launched. 
//--- 
//    iDateTime       - date and time in MT4 format, passed from MT4
//    sSymbol         - symbol
//    cAsk            - quote Ask
//    cBid            - quote Bid
//
CREATE TABLE [dbo].[MT4TICK] (
    [idc] [bigint] IDENTITY (1, 1) NOT NULL ,
    [ServerDateTime] [datetime] NULL ,
    [iDateTime] [bigint] NULL ,
    [sSymbol] [char] (6) COLLATE SQL_Latin1_General_CP1251_CI_AS NULL ,
    [cAsk] [numeric](18, 4) NULL ,
    [cBid] [numeric](18, 4) NULL 
) ON [PRIMARY]
GO
 
--- Include automated filling out the ServerDateTime field with the date and time of server MS SQL
ALTER TABLE [dbo].[MT4TICK] ADD 
    CONSTRAINT [DF_MT4TICK_ServerDateTime] DEFAULT (getdate()) FOR [ServerDateTime]
GO

以下は表示されるプロシージャをティックが受け取り表にする方法です。


// 
//    @RetCode int out          --- used for returning
//   ,@psSymbol char(6)         --- symbol
//   ,@piDateTime  bigint       --- date and time of tick arrival
//   ,@pdAsk  float             --- Ask 
//   ,@pdBid  float             --- Bid
//  
//   The procedure just returns 0 
//     if we analyze the code of returning to MQL4, we can see that the quote has reached the procedure and has been tabulated
//     
//
CREATE PROCEDURE dbo.YZ_MT4_TICK
    @RetCode int out          
   ,@psSymbol char(6)
   ,@piDateTime  bigint
   ,@pdAsk  float
   ,@pdBid  float
AS
insert into  MT4TICK   ( sSymbol, iDateTime, cAsk, cBid   )  values  ( @psSymbol , @piDateTime,  @pdAsk ,  @pdBid  )
select @RetCode=0
return @RetCode


上記説明から、どの目的にためにどの手順が使用されるかわかります。

@RetCode -DLL から渡されるときは何も機能を持ちません。ターミナルコードを受け取る役目を果たすだけです。

MS SQL SERVER の設定が終わりました。標準的なコンフィギュレーションを作成するスクリプトは本稿に添付されています。


想像しましょう。可能なソリューション、そしてプラスα

データストレージを作成し、そこに情報を出し入れします。このように、MT 4 クライアントターミナルをクオート履歴を格納する必要性から解放します。次に、クオート履歴はに格納され、この情報で作業し、すぐにそれを抽出し、別のアプリケーションにエクスポートすることができます。NEURAL パッケージで分析するデータを使用することができます。そのほとんどは SQL ストレージと連携可能です。

リアルタイムでターミナルはインディケータからのシグナルを形成し、ストレージに私、この方法で修正し続けます。外部アプリケーションはシグナルと履歴をリアルタイムで抽出し、分析し、実行との MS SQL Server ストレージを修正しながらシグナルを形成し、実行するためにターミナルへ送信します。

このように、自動化されたトレーディング複合体に関与するアプリケーション間での統合と機能分配ができるです。

履歴クオートを格納する必要がもうなければ、それを以下のように設定します。最小バー、たとえば5000を Tools → Options → Chartsで設定します。ターミナルはより速く動作し始めます。というのも、大きな履歴についてのメモリを割り当てる必要がないためです。





ソーステキスト

DLL コード

//+------------------------------------------------------------------+
//|                                              Sample DLL for MQL4 |
//|                 Copyright c 2004-2008, MetaQuotes Software Corp. |
//|                                        https://www.metaquotes.net |
//+------------------------------------------------------------------+
 
//+------------------------------------------------------------------+
//
//  YURAZ 2008  YZMSSQLExpertSample
//
//  Example DLL Integrating  MT4 with MS SQL 2000
//
//  ADO  MS SQL SERVER
//
//  software used
//
//  VISUAL C++ 6 , SP5 ,  MDAC 7 ,  MS SQL2000 + SP4
//
//+------------------------------------------------------------------+
  
#define WIN32_LEAN_AND_MEAN  // Exclude rarely-used stuff from Windows headers
#include <windows.h>
#include <stdlib.h>
#include <stdio.h>
//----
#define MT4_EXPFUNC __declspec(dllexport)
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
#pragma pack(push,1)
 
struct RateInfo
  {
   unsigned int      ctm;
   double            open;
   double            low;
   double            high;
   double            close;
   double            vol;
   double            vol1;
   double            vol2;
   double            vol3;
   double            vol4;
   double            vol5;
 
  };
 
#pragma pack(pop)
   
struct MqlStr
  {
   int               len;
   char             *string;
  };
  
static int CompareMqlStr(const void *left,const void *right);
   
static int SQLexecProcedure( char *nprc );
static int SQLexecProcedureSignal( char *sSymbol, char* sProcedure );
// static int _YZSQLsqlstrinsql( char *Symbol , unsigned int DateTime , double Ask, double Bid, char *NamePrc );
static int _YZSQLprocedure  ( char *sSymbol, unsigned int pDateTime, double Ask, double Bid, char *NamePrc );
static int _YZSQLprocedureHISTORYPut(char *Symbol,unsigned int Period, unsigned int DateTime,double Open,
                        double High,double  Low, double Close ,double Volume, unsigned int Bar ,char *Procedure);
 
                                                                                                             
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved)
  {
//----
   switch(ul_reason_for_call)
     {
      case DLL_PROCESS_ATTACH:
      case DLL_THREAD_ATTACH:
      case DLL_THREAD_DETACH:
      case DLL_PROCESS_DETACH:
         break;
     }
//----
   return(TRUE);
  }
 
 // place ticks in MS SQL
 // call the procedure as an SQL line passing parameters   "exec YZ_MT4_TICK ?,?,?,?"
/*
  MT4_EXPFUNC int  __stdcall SQLsqlstringTickPut(char *Symbol,unsigned int DateTime,double Ask,double Bid,char *sSQLstring)
 {
    int ccc =  _YZSQLsqlstrinsql( Symbol  , DateTime ,  Ask , Bid  , sSQLstring  );
    return(ccc);
 }
*/
 
 // call as a procedure passing parameters
  MT4_EXPFUNC int  __stdcall SQLProcedureTickPut(char *Symbol,unsigned int DateTime,double Ask,double Bid,char *Procedure)
 {
    int ccc =  _YZSQLprocedure( Symbol  , DateTime ,  Ask , Bid  ,Procedure );
    return(ccc);
 }
 
 // place a specific candlestick in MS SQL history
 MT4_EXPFUNC int  __stdcall SQLProcedureHistoryPut(char *Symbol,unsigned int Period , unsigned int DateTime,
                double Open,double High,double  Low, double Close ,double Volume,unsigned int Bar ,char *Procedure)
 {
    int ccc  =  _YZSQLprocedureHISTORYPut(Symbol,Period,DateTime,Open,High,Low,Close,Volume,Bar,Procedure);
    return(ccc);
 }
 

 // call procedure sProcedure
 // 
 // return -1 error
 //
 MT4_EXPFUNC int  __stdcall SQLProcedureGetInt(char *sProcedure)
 {
        int Ret =    SQLexecProcedure( sProcedure );
     return((int)Ret);
 }
 

 MT4_EXPFUNC int  __stdcall SQLProcedureGetSignal  (char *sSymbol, char *sProcedure)
 {
     
     int Ret =    SQLexecProcedureSignal( sSymbol, sProcedure );
     return((int)Ret);
 }
  
//////////////////////////////////
#include "stdafx.h"
#include <stdio.h>
#import "C:\Program Files\Common Files\System\ado\msado20.tlb" \
        rename("EOF","ADOEOF") rename("BOF","ADOBOF")
 
using namespace ADODB;
  
inline void TESTHR(HRESULT x) { if FAILED(x) _com_issue_error(x); };
 
// procedure call method
int _YZSQLprocedure( char *sSymbol, unsigned int pDateTime, double Ask, double Bid,   char *NamePrc )
{
  
   HRESULT hr = S_OK;
   _CommandPtr pCmd = NULL;
   _ConnectionPtr pConnection = NULL;
   _bstr_t strMessage, strAuthorID;
 
       ::CoInitialize(NULL);
 
   long codRet = -1;
 
   try {
      
      _ParameterPtr Par1;
      _ParameterPtr Par2;
      _ParameterPtr Par3;
      _ParameterPtr Par4;
      _ParameterPtr Par5;
 
      TESTHR(pConnection.CreateInstance(__uuidof(Connection)));
      hr = pConnection->Open("dsn=MT4_SQL_BASE;", "yuraz", "qwerty", adConnectUnspecified);
      pConnection->CursorLocation = adUseClient;
      TESTHR(pCmd.CreateInstance(__uuidof(Command)));
      pCmd->CommandText = NamePrc;  // procedure name
      pCmd->CommandType = adCmdStoredProc;
     
      Par1 = pCmd->CreateParameter( _bstr_t("@P1"), adInteger,   adParamOutput,0,    codRet );
      pCmd->Parameters->Append( Par1 );
      Par1 = pCmd->CreateParameter("@psSymbol",adChar, adParamInput, strlen(sSymbol) ,sSymbol );
         pCmd->Parameters->Append(Par1);
      Par2 = pCmd->CreateParameter("@piDateTime", adDouble , adParamInput, sizeof(double) ,  (double)pDateTime );
      pCmd->Parameters->Append(Par2);
      Par3 = pCmd->CreateParameter("@pdAsk", adDouble, adParamInput, 4, Ask );
      pCmd->Parameters->Append(Par3);
      Par4 = pCmd->CreateParameter("@pdBid", adDouble, adParamInput, 4, Bid );
      pCmd->Parameters->Append(Par4);
 
      
      pCmd->ActiveConnection = pConnection;
      int hr = pCmd->Execute( 0, 0, adCmdStoredProc );
      if( FAILED(hr) )
      {
                codRet = -1;
      }
      else
      {
         Par1 = pCmd->Parameters->GetItem(_bstr_t("@P1"));     // obtain from the procedure
         codRet = Par1->GetValue();
      }
   }
   catch(_com_error  ) {
       //
       // if necessary, process the execution error
          //
       codRet = -1;
 
   }
   if (pConnection)
      if (pConnection->State == adStateOpen)
         pConnection->Close();
 
   ::CoUninitialize();
    return((int)codRet);
}
 


// place in history Symbol , Period . DateTime, Open , High , Low , Close , Value , Bar
int _YZSQLprocedureHISTORYPut(char *pSymbol,unsigned int pPeriod, unsigned int pDateTime,double pOpen,double pHigh,
                                        double  pLow, double pClose ,double pVolume, unsigned int pBar ,char *pProcedure )
{
 

        HRESULT hr = S_OK;
   _CommandPtr pCmd = NULL;
   _ConnectionPtr pConnection = NULL;
   _bstr_t strMessage, strAuthorID;
 
       ::CoInitialize(NULL);
 
   long codRet = -1;
 
   try {
 
      _ParameterPtr ParReturn; // 
      _ParameterPtr Par1; // SYMBOL
      _ParameterPtr Par2; // PERIOD
      _ParameterPtr Par3; // DATETIME
      _ParameterPtr Par4; // OPEN
      _ParameterPtr Par5; // HIGH
      _ParameterPtr Par6; // LOW
      _ParameterPtr Par7; // CLOSE
      _ParameterPtr Par8; // VOLUME
      _ParameterPtr Par9; // BAR
 

      TESTHR(pConnection.CreateInstance(__uuidof(Connection)));
      hr = pConnection->Open("dsn=MT4_SQL_BASE;", "yuraz", "qwerty", adConnectUnspecified);
      pConnection->CursorLocation = adUseClient;
      TESTHR(pCmd.CreateInstance(__uuidof(Command)));
      pCmd->CommandText = pProcedure;  // procedure name
      pCmd->CommandType = adCmdStoredProc;
     
      ParReturn = pCmd->CreateParameter( _bstr_t("@P1"), adInteger,   adParamOutput,0,    codRet );
      pCmd->Parameters->Append( ParReturn );
 
      Par1 = pCmd->CreateParameter("@psSymbol",adChar, adParamInput, strlen(pSymbol) ,pSymbol );
         pCmd->Parameters->Append(Par1);
 
      Par2 = pCmd->CreateParameter("@piDateTime", adDouble , adParamInput, sizeof(double) ,  (double)pPeriod );
      pCmd->Parameters->Append(Par2);
 
      Par3 = pCmd->CreateParameter("@piDateTime", adDouble , adParamInput, sizeof(double) ,  (double)pDateTime );
      pCmd->Parameters->Append(Par3);
 
      Par4 = pCmd->CreateParameter("@pdOpen", adDouble, adParamInput, 4, pOpen );
      pCmd->Parameters->Append(Par4);
 
      Par5 = pCmd->CreateParameter("@pdHigh", adDouble, adParamInput, 4, pHigh );
      pCmd->Parameters->Append(Par5);
 
      Par6 = pCmd->CreateParameter("@pdLow", adDouble, adParamInput, 4, pLow );
      pCmd->Parameters->Append(Par6);
 
      Par7 = pCmd->CreateParameter("@pdClose", adDouble, adParamInput, 4, pClose );
      pCmd->Parameters->Append(Par7);
      
      Par8 = pCmd->CreateParameter("@pdVolume", adDouble, adParamInput, 4, pVolume );
      pCmd->Parameters->Append(Par8);
 
      Par9 = pCmd->CreateParameter("@piBar", adDouble , adParamInput, sizeof(double) ,  (double)pBar );
      pCmd->Parameters->Append(Par9);
 

      pCmd->ActiveConnection = pConnection;
      int hr = pCmd->Execute( 0, 0, adCmdStoredProc );
      if( FAILED(hr) )
      {
                codRet = -1;
      }
      else
      {
         ParReturn = pCmd->Parameters->GetItem(_bstr_t("@P1"));     // obtain from the procedure
         codRet = ParReturn->GetValue();
      }
   }
   catch(_com_error  ) {
       //
       // if necessary, process the execution error
          //
       codRet = -1;
 
   }
   if (pConnection)
      if (pConnection->State == adStateOpen)
         pConnection->Close();
 
   ::CoUninitialize();
    return((int)codRet);
}
 

//
// return the value returned by the procedure
//
int  SQLexecProcedure( char *nprc )
{
   
    HRESULT hr = S_OK;
   _CommandPtr pcmd = NULL;
   _ConnectionPtr pConnection = NULL;
   _bstr_t strMessage, strAuthorID;
 
       ::CoInitialize(NULL);
 
   long codRet = -1;
 
   try {
      TESTHR(pConnection.CreateInstance(__uuidof(Connection)));
      hr = pConnection->Open("dsn=MT4_SQL_BASE;", "yuraz", "qwerty", adConnectUnspecified);
      pConnection->CursorLocation = adUseClient;
      TESTHR(pcmd.CreateInstance(__uuidof(Command)));
      pcmd->CommandText = nprc;  // procedure name
      pcmd->CommandType = adCmdStoredProc;
     
      _ParameterPtr  pParm1 = pcmd->CreateParameter( _bstr_t("@P1"), adInteger,   adParamOutput,0,    codRet );
      pcmd->Parameters->Append( pParm1 );
      pcmd->ActiveConnection = pConnection;
      int hr = pcmd->Execute( 0, 0, adCmdStoredProc );
      if( FAILED(hr) )
      {
                codRet = -1;
      }
      else
      {
         pParm1 = pcmd->Parameters->GetItem(_bstr_t("@P1"));     // obtain from the procedure
         codRet = pParm1->GetValue();
      }
   }
   catch(_com_error  ) {
       //
       // if necessary, process the execution error
          //
       codRet = -1;
 
   }
   if (pConnection)
      if (pConnection->State == adStateOpen)
         pConnection->Close();
 
   ::CoUninitialize();
    return((int)codRet);
}
 
//
//
//
int  SQLexecProcedureSignal( char *sSymbol, char* sProcedure )
{
   
    HRESULT hr = S_OK;
   _CommandPtr pcmd = NULL;
   _ConnectionPtr pConnection = NULL;
   _bstr_t strMessage;
   _bstr_t strAuthorID;
 
       ::CoInitialize(NULL);
 
   long codRet = 0;
 
   try {
      TESTHR(pConnection.CreateInstance(__uuidof(Connection)));
      hr = pConnection->Open("dsn=MT4_SQL_BASE;", "yuraz", "qwerty", adConnectUnspecified);
      pConnection->CursorLocation = adUseClient;
      TESTHR(pcmd.CreateInstance(__uuidof(Command)));
      pcmd->CommandText = sProcedure;  // procedure name
      pcmd->CommandType = adCmdStoredProc;
 
      _ParameterPtr pParm1 = pcmd->CreateParameter("@psSymbol",adChar, adParamInput, strlen(sSymbol) ,sSymbol );
      pcmd->Parameters->Append(pParm1);
      _ParameterPtr pParm2 = pcmd->CreateParameter( _bstr_t("@P1"), adInteger,   adParamOutput,0,    codRet );
      pcmd->Parameters->Append( pParm2 );
      pcmd->ActiveConnection = pConnection;
      int hr = pcmd->Execute( 0, 0, adCmdStoredProc );
            if( FAILED(hr) )
            {
                bool bSuccess = false;
            }
            pParm2 = pcmd->Parameters->GetItem(_bstr_t("@P1"));     // obtain from the procedure
            codRet = pParm2->GetValue();
 
//             printf("\n [%d] \n",codRet );       // OBTAINING from the procedure
   }
   catch(_com_error  ) {
       //
       // if necessary, process the execution error
          //
   }
   if (pConnection)
      if (pConnection->State == adStateOpen)
         pConnection->Close();
 
   ::CoUninitialize();
    return((int)codRet);
}


MQL4 からの呼出し例

// Comments are reduced to make it appear simpler, the comments in the attached files are complete
 
//+------------------------------------------------------------------+
//|                                                                  |
//|                 Copyright c 1999-2006, MetaQuotes Software Corp. |
//|                                         http://www.metaquotes.ru |
//|                                                YZMSSQLSample.mq4 |
//|                                                   Yuriy Zaitsev  |
//+------------------------------------------------------------------+
// Example of integrating with MS SQL                                |
//+------------------------------------------------------------------+
 
#property copyright "YURAZ Copyright(C) 2008"
#property link      "yzy @ mail.ru"
 
//+------------------------------------------------------------------+
// DLL function library 
//+------------------------------------------------------------------+
#import "YZMSSQLExpertSample.dll"
// Performing any actions on MS SQL Server, procedure is called
SQLProcedureGetInt 
// Collecting ticks
int SQLProcedureTickPut( string,  int , double , double ,string );  
 
int Prc = 0;
int init()
  {
 
//
// SQLProcedureGetInt The function, once having called a certain procedure, 
// will return into MT4 int value, for example, parameters
// stored on MS SQL server, formed by another software
//
   Prc =     SQLProcedureGetInt ("YZ_MT4_T1"); 
   return(0);
  }
 
int start()
  {
   int a;
 
   int RetCode = SQLProcedureTickPut( Symbol(), TimeCurrent() , Ask, Bid ,"YZ_MT4_TICK"); // call to the tick collecting procedure
   Print(" SQLProcedureTickPut (YZ_MT4_NEWDAY)"+ RetCode );
 
// Example:
//    on MS SQL server, you can filter signals formed using third-party software
//    neural networks 
//    other software products 
//
/*
   int Signal = SQLProcedureGetSignal (Symbol() , "YZ_MT4_SIGNAL" ); // procedure MS SQL , will return signal
   Print(" SQLProcedureGetSignal (Symbol() , YZ_MT4_SIGNAL )"+ Signal );
   if ( Signal == OP_BUY )
   {
       // the procedure has returned the signal and is recommending to buy
   }
   if ( Signal == OP_SELL )
   {
       // the procedure has returned the signal and is recommending to sell
   }
*/
 
   return(0);
  }

MS SQL Server へ履歴をロードするスクリプト

//
// YURAZ  2008 yzh @ mail.ru
//
// script loading history onto MS SQL
// reload all history for all currency pairs and for all TIMEFRAMES
// in MS SQL
//
 
#import "YZMSSQLExpertSample.dll"
int SQLProcedureHistoryPut( string,  int  , int, double , double ,double , double ,double ,int,  string );  
 
static int mPeriod[8]={PERIOD_M1,PERIOD_M5,PERIOD_M15,PERIOD_M30,PERIOD_H1,PERIOD_H4,PERIOD_D1,PERIOD_W1,PERIOD_MN1};
 
void start()
{
    PutHistor("EURUSD"); 
    PutHistor("USDCHF"); 
    Comment(" LOADING COMPLETE " );
}
 
void PutHistor(string sSymbol)
{
  for ( int iPeriod = 0; iPeriod <= 8 ; iPeriod++ )
  {
     int pPERIOD_XX = mPeriod[iPeriod];
      int Bar = iBars(sSymbol,pPERIOD_XX ); // obtain the depth of history for the given timeframe
 // no progress bar organized 
     for ( int iBar = Bar; iBar >= 0 ; iBar--)
     {
     Comment( "WAIT  TIMEFRAME "+pPERIOD_XX+" SYMBOL "+sSymbol+" BARS "+iBar );
       double   o = iOpen  (sSymbol,pPERIOD_XX,iBar);
       double   h = iHigh  (sSymbol,pPERIOD_XX,iBar);
       double   l = iLow   (sSymbol,pPERIOD_XX,iBar);
       double   c = iClose (sSymbol,pPERIOD_XX,iBar);
       double   v = iVolume(sSymbol,pPERIOD_XX,iBar);
       datetime d = iTime  (sSymbol,pPERIOD_XX,iBar);
       int RetCode = SQLProcedureHistoryPut( sSymbol,pPERIOD_XX,d,o,h,l,c,v,iBar, "YZ_MT4_HISTORY");
       // Print ( " YZ_MT4_HITSRY "+RetCode);
      }
  }
}

注意:残念ながら、スクリプトを使用すると全履歴のロードはかなり遅くなりますが、それは明らかにハイクオリティーでバー数を修正します。

最良のソリューションはクオートをテキストファイルにアンロドし、それを IMPRT EXPORT DTS によって MS SQL にロードすることです。各シンボルについて 1999~2008 の M1 履歴をロードするのにかかるのは数分です。
テキストファイルへアンロードする際、バーインデックスはアンロードされません。バーインデックスをただの行番号とするのであれば、漏れたバーの問題が起こり、変更したり再ロードする場合、アンロードされたバーの番号は MS SQL や MT 4 にあるのと異なる可能性があります。この問題はまだ解決していませんが、MT 4 自体でハイクオリティーな履歴更新後履歴を再ロードすることで解決できると考えています。


添付ファイルの説明

CreateSQLallDate.txt (9.0 Kb)

-MS SQL Server でベース、テーブル、プロシージャ作成方法例としての SQL 形式のスクリプト

SQLGETHISTORY.mq4 (1.4 Kb)

- MS SQL に履歴をロードするスクリプト

YZMSSQLExpertSample.rar (89.9 Kb)

- DLL project

YZMSSQLSample.mq4 (13.1 Kb) -

シンボルチャートに EA としてアタッチするために、そのティックを収集する必要があります。それは任意のタイムフレームにアタッチ可能です。


おわりに

別のソフトウェア製品と統合することは、MetaTrader 4 の機能性を広げ、自動トレーディングシステムのタスクと関数を効率的に分配することを可能にします。


MetaQuotes Ltdによってロシア語から翻訳されました。
元の記事: https://www.mql5.com/ru/articles/1533

添付されたファイル |
SQLGETHISTORY.mq4 (1.45 KB)
YZMSSQLSample.mq4 (13.07 KB)

この著者による他の記事

非トレード EA 検証インディケータ 非トレード EA 検証インディケータ
インディケータはすべて2グループに分けることができます。静的インディケータ。それの表示は一度示されると常に履歴で同じままで、新規の着信クオートで変化することはありません。動的インディケータ。現在の変動に対する状態のみ表示し、新価格が来ると完全に再描画されます。静的インディケータの効率は直接チャートで見ることができます。動的インディケータが正常に動作しているかどうか確認するには?本稿が取り組むのはこの疑問です。
ショウは続く- または ZigZag 再び。 ショウは続く- または ZigZag 再び。
ZigZag 構成の明確であるがまだサブスタンダートな方法について、そしてそれがどんな結果につながるか:単一のタイムフレーム(TF)にて、3つの大きなものに構築される ZigZag を表現するマルチフレーム フラクタル ZigZag インディケータ、について取り上げます。そこでは、それら大きなは標準的ではなく、範囲は M5~MN1です。
一般的トレーディングシステムを基にした Expert Advisors と売買ロボット最適化の錬金術(パート6) 一般的トレーディングシステムを基にした Expert Advisors と売買ロボット最適化の錬金術(パート6)
本稿では、先行記事で紹介したトレーディングシステムを改良する方法を提案します。本稿は、Expert Advisor のプログラミング経験をすでにお持ちのトレーダーの方々にとって興味深いものとなるでしょう。
誤った考え、パート2統計は、偽りの科学か、暴落するなくてはならない歴史です。 誤った考え、パート2統計は、偽りの科学か、暴落するなくてはならない歴史です。
統計的なメソッドに客観的な現実、つまり金融上の出来事に適用とする試みは、不十分なデータや、確率分布やプロセスの非定常性に直面し、虚しく失敗してしまっています。この記事では、そのような金融上の出来事ではなく、主観的な意見を記述し、トレーダーがどのようにこれらを防ごうとしたか、トレーダーシステムについて記述します。トレーディング結果の統計的な規則性の抽出は、むしろ大変面白い作業です。時折、このプロセスのそのモデルに関する結論が導かれ、これらがトレーディングシステムに適用されます。