エラー、バグ、質問 - ページ 2639

 
Aleksey Vyazmikin:

ひょっとして、ポータブルモードキーが必要なのでしょうか?

すべての端末は手動で起動するのですか?

手で、そう、みんなそうなんです。結局、そうやって手動で起動させた。

この点については、携帯モードキーを使っても何も変わりません。

MT4では認証ウィンドウが表示され、プログラムの起動が完了したとみなされないことです。

バッチファイル内で "start "を使用する必要があります。

結局のところ、私はこのことを理解したのです。

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

 
Petros Shatakhtsyan:

これでもまだ理解できないってことは、私の書き込みをよく読んでないんでしょうね。私が訴えたいのは、あなたではなく、開発者の 方です。安直なアドバイスはいらない。

落ち着いて、そんなに心配しないでください。

改めて、脳の発達が低い人は普段から礼節を理解していないのだと納得しました。

もっと知識のある人に言われたことも理解できず、字もまともに書けない幼稚園児のような無礼者。

 
残念ながら、いや幸いなことに、私は直接の開発はしていないんです。
しかし、プロジェクトに取り組むからこそ、その言語の能力を 見極め、不具合やバグを発見することができる...。

従来は、MQLプロジェクトに取り組む際、不具合(バグ)の情報は、発見された順に提供されていました。
そこで、新たな試みとして、ブロック化された不具合までの作業を行い、検出された全ての不具合について情報を提供することにしました。
 
#ifdef __cplusplus
   #include <iostream>
#endif 

#define  PRINT(x) ; Print(#x, ":", string(x))


template<typename T>
class main_wrapper{
public:
   T data;
};

template<typename T>
class external_wrapper{
public:
   T data;
};

template<typename T>
class A{
public:
   class internal_wrapper : public external_wrapper<T> {};
   
   main_wrapper<internal_wrapper> internal_wrapper_0;
   main_wrapper<external_wrapper<T>> external_wrapper_0;
   
   A(){
        main_wrapper<internal_wrapper> internal_wrapper_1;
        main_wrapper<external_wrapper<T>> external_wrapper_1;
   
        #ifdef __MQL5__
            PRINT(__FUNCSIG__);
            PRINT(typename(internal_wrapper_0.data.data));      // (Bug) int  int
            PRINT(typename(external_wrapper_0.data.data));      // (OK)  int  B*
            PRINT(typename(internal_wrapper_1.data.data));      // (Bug) int  int
            PRINT(typename(external_wrapper_1.data.data));      // (OK)  int  B*
        #endif
   }
};

class B{
   char data[10];
};

class C{
   char data[1000];
};


void OnStart()
{ 
   A<int> val_int;
   A<B*> val_ptr;
   
   printf("%d\n", sizeof(main_wrapper<A<B>::internal_wrapper>));  // (Bug) 36  //sizeof(main_wrapper<A<int>::internal_wrapper>) is used
   printf("%d\n", sizeof(main_wrapper<A<C>::internal_wrapper>));  // (Bug) 36  //sizeof(main_wrapper<A<int>::internal_wrapper>) is used
}

int main(){
   OnStart();
   return 1;
}
MT5(ビルド2316)の非常に厄介なバグがあり、今後の開発を阻害しています。
内部型 "C "の複雑なラップオブジェクトを何度も作成したが、結局は全く別のデータ型、"B"、"int"、何でもいいのだが......。

問題はコードにあるのではなく、MQLコンパイラにあることを発見し理解するのに多くの時間と労力を要しました。(C++ オンライン: https://onlinegdb.com/H1R1fR5ML)
おそらく、テンプレート・クラス「A」の内部クラス「internal_wrapper」を異なるデータ型(int、B*、B、C)のパラメータとして渡す場合のコンパイル時のコード生成時のテンプレート・クラス「main_wrapper」キャッシュの働きに問題があるものと思われます。
最初のデータ型は、テンプレート・クラス「main_wrapper<A<TEMPLATE_TYPE>::internal_wrapper>」によって作られ、このデータ型は将来、テンプレートの全てのオブジェクトでさらに使われることになります。


また、テンプレート・クラス・コードの生成に関するバグについては、後述します。
 
class A{
public:
   class B{};
};

template<typename T>
class wrapper{
public:
   T data;
};

template<typename T>
class wrapped_B{
public:
   A::B data;
};
   
void OnStart()
{ 
   A::B a;                // OK
   wrapper<A::B> b0;      // 'B' - unexpected token, probably type is missing?  'data' - semicolon expected     
   
   wrapped_B<A::B> b2;    // OK
   
   class local_B : public A::B{};
   wrapper<local_B> b1;   // OK
}


int main(){
   OnStart();
   return 0;
}

MT5(build2316)で内部クラス使用時のテンプレートクラスコード生成の不具合を修正しました。
C++オンライン: https://onlinegdb.com/HJkKXAqMU

 
template<typename T>
class type_wrapper{
    T data;
};

template<typename T>
class A{
   class type_wrapper : public :: type_wrapper<T>{}; // '::' - syntax error      
};

void OnStart()
{ 
   A<int> a;
}


int main(){
   OnStart();
   return 0;
}

内部クラスに関するMT5(build 2316)の もう一つの不具合は、グローバル名前空間を明示的に参照することができないことです。
C++オンライン: https://onlinegdb.com/H14NF05G8

 
Sergey Dzyublik:
今後の開発を阻む非常に厄介なバグ。
内部型 "C "の複雑なラップオブジェクトを何度も作成したが、結局は全く別のデータ型、"B"、"int"、何でもいいのだが......。

多くの時間と労力を費やし、問題はコードにあるのではなく、MQLコンパイラにあることを発見し理解することができました。(C++ オンライン: https://onlinegdb.com/H1R1fR5ML)
おそらく、テンプレート・クラス「A」の内部クラス「internal_wrapper」を異なるデータ型(int、B*、B、C)のパラメータとして渡す場合のコンパイル時のコード生成時のテンプレート・クラス「main_wrapper」キャッシュの働きに問題があるものと思われます。
最初のデータ型は、テンプレート・クラス「main_wrapper<A<TEMPLATE_TYPE>::internal_wrapper>」によって作られ、このデータ型は将来、テンプレートの全てのオブジェクトでさらに使われることになります。


また、テンプレート・クラス・コードの生成に関するバグについては、後述します。
#ifdef __cplusplus
   #include <iostream>
#endif 

#define  PRINT(x) ; Print(#x, ":", string(x))


template<typename T>
class main_wrapper{
public:
   T data;
};

template<typename T>
class external_wrapper{
public:
   T data;
};

template<typename T>
class A{
public:
   template<typename T1>
   class internal_wrapper : public external_wrapper<T1> {};
   
   main_wrapper<internal_wrapper<T>> internal_wrapper_0;
   main_wrapper<external_wrapper<T>> external_wrapper_0;
   
   A(){
        main_wrapper<internal_wrapper<T>> internal_wrapper_1;
        main_wrapper<external_wrapper<T>> external_wrapper_1;
   
        #ifdef __MQL5__
            PRINT(__FUNCSIG__);
            PRINT(typename(internal_wrapper_0.data.data));      // (Bug) int  int
            PRINT(typename(external_wrapper_0.data.data));      // (OK)  int  B*
            PRINT(typename(internal_wrapper_1.data.data));      // (Bug) int  int
            PRINT(typename(external_wrapper_1.data.data));      // (OK)  int  B*
        #endif
   }
};

class B{
   char data[10];
};

class C{
   char data[1000];
};


void OnStart()
{ 
   A<int> val_int;
   A<B*> val_ptr;
   
   printf("%d\n", sizeof(main_wrapper<A<B>::internal_wrapper<B>>));  // (Bug) 36  //sizeof(main_wrapper<A<int>::internal_wrapper>) is used
   printf("%d\n", sizeof(main_wrapper<A<C>::internal_wrapper<C>>));  // (Bug) 36  //sizeof(main_wrapper<A<int>::internal_wrapper>) is used
}
これでいいのでしょうか?
 
Vladimir Simakov:
このやり方で良いのでしょうか?

ありがとうございます。確かに例の場合、ダミーのテンプレートパラメータを導入することで、問題を回避することができます。
しかし、グローバルプロジェクトに関しては、もう少し複雑です。開発プロセスと最終的なコンテナクラスの適用の両方を単純化するために、不足しているtypedef typename機能の代わりに内部クラスが 使用されました。
開発元からの修正を待つ価値はあるかもしれません。
最後の手段として、すべての依存関係を外部に引きずり出し、実行時に未定義の動作でこれ以上コンパイルが成功しないことを祈るしかないだろう。

 

内部クラスの機能をまとめると
を正しく使うには、少なくともその原始的な形である typedef 宣言の機能が欠けていることは明らかです......。
だから、かなりコンパクトで理解しやすいC++のコードではなく

template <class _Tp, class _Allocator>
class vector
    : private __vector_base<_Tp, _Allocator>
{
private:
    typedef __vector_base<_Tp, _Allocator>           __base;
public:
    typedef vector                                   __self;
    typedef _Tp                                      value_type;
    typedef _Allocator                               allocator_type;
    typedef typename __base::__alloc_traits          __alloc_traits;
    typedef typename __base::reference               reference;
    typedef typename __base::const_reference         const_reference;
    typedef typename __base::size_type               size_type;
..............................


defineと内部クラスによる継承でフェンスを構築する必要がある。

template<typename _Tp, typename _Allocator>
class __vector_base{
public:
   class allocator_type    : public _Allocator{}; 
   
protected:
   #define  value_type          _Tp
   #define  size_type           DEFAULT_SIZE_TYPE
   #define  difference_type     size_type
   
   struct pointer          : public allocator_type::pointer{};
   struct iterator         : public allocator_type::pointer{};
............................

   #undef  value_type
   #undef  size_type
   #undef  difference_type
};


そして、ここには一見してわからないほど多くの問題があるのです。
defineをtypedef宣言として使用した場合、問題が発生します。

- クラス外で使用されるデータの型を渡す方法がない(単純なデータ型を 渡す方法が全くない)。
- defineのスコープを対応する#undefのペアで常に制御する必要があります。

内部クラスを typedef 宣言として使用した場合の問題点。

-
- 継承するとコンストラクタが使えなくなるので、ベースクラスのシグネチャを使って手動で書き直す必要がある。
- typedef宣言が使われているクラスにベースクラスがある場合、名前空間の重複によってtypedef宣言と同じ名前を使うことはできない。
 
デフォルトの代入演算子を導入したため、ベースクラスに対してランダムな代入の実行を禁止する必要が生じました。
開発者は、この目的のために「operator= delete」を追加しました。
しかし、削除/デフォルトのリンクを解除すると、すべてを手動で書き直す必要があるため、論理的ではないように思われます。
もしかして、私のやり方が悪いのか?

class Base{
    char base_data[100];
};

template<typename T>
class A : public Base{
   int data_1;
   int data_2;
   int data_3;
   int data_4;
   int data_5;
   int data_6;
   int data_7;
   int data_8;
   int data_9;
   
   char arr_1[];
   char arr_2[];
public:    
   // MQL
   A* operator=(A &obj){
      data_1 = obj.data_1; 
      data_2 = obj.data_2; 
      data_3 = obj.data_3; 
      data_4 = obj.data_4; 
      data_5 = obj.data_5; 
      data_6 = obj.data_6; 
      data_7 = obj.data_7; 
      data_8 = obj.data_8; 
      data_9 = obj.data_9; 
      
      ArrayCopy(arr_1, obj.arr_1);
      ArrayCopy(arr_2, obj.arr_2); 
      
      (Base)this = obj;
      return &this;
   };
   
   // C++
   // A& operator=(A &) = default;
    
   template<typename TT>
   A* operator=(A<TT> &) = delete;
};

void OnStart()
{ 
   A<int> a;
   A<int> b;
   
   A<double> c;
   
   a = b;      
   //a = c;       
}