記事「PythonからMQL5へ:量子に着想を得た取引システムへの旅」についてのディスカッション

 

新しい記事「PythonからMQL5へ:量子に着想を得た取引システムへの旅」はパブリッシュされました:

この記事では、量子に着想を得た取引システムの開発について検討し、Pythonプロトタイプから実際の取引のためのMQL5実装への移行について説明します。このシステムは、量子シミュレーターを使用した従来のコンピューター上で実行されますが、重ね合わせや量子もつれなどの量子コンピューティングの原理を使用して市場の状態を分析します。主な機能には、8つの市場状態を同時に分析する3量子ビットシステム、24時間のルックバック期間、および市場分析用の7つのテクニカル指標が含まれます。精度率は控えめに思えるかもしれませんが、適切なリスク管理戦略と組み合わせると大きな優位性が得られます。

量子コンピューティングの理論的なアイデアと現実世界の取引アプリケーションを結び付ける旅に出て、量子に着想を得た取引システムを徹底的に探求します。本チュートリアルでは、基本的な量子コンピューティングの概念から始め、最終的にMQL5への実装までを体系的に解説します。量子概念の使用によって取引がどのように恩恵を受けるかについて議論し、PythonプロトタイプからMQL5の統合までの開発アプローチについて説明し、実際のパフォーマンスデータとコード実装を紹介します。 

この記事では、量子コンピューティングの理論とMQL5での実践的な実装を結び付け、取引システムにおける量子に着想を得た手法の応用について解説します。基本的な量子原理を紹介し、PythonによるプロトタイピングからMQL5への統合までの流れを、実際のパフォーマンスデータを交えながら説明します。

従来の取引はバイナリな意思決定に依存していますが、量子に着想を得た取引モデルは、市場の挙動を量子現象に類似した形で捉えます。具体的には、複数の同時状態、相互依存、突然の状態変化などの概念を取り入れることで、より柔軟で適応的な取引戦略を実現できます。Qiskitのような量子シミュレーターを活用することで、従来のコンピューター上で量子に着想を得たアルゴリズムを実装し、市場の不確実性に対処しながら、より高度な予測的洞察を得ることが可能になります。


作者: Javier Santiago Gaston De Iriarte Cabrera

 
設定2は使わないでください(最適化しっぱなしで負け戦略でした)。最適化を行い、最適なものを探してください(そしてEAを完成させてください)。
 

量子コンピューティングについては詳しくないのですが、以前から興味を持っていました。

この具体的な実装について、AIに質問を送りました――難癖をつけるためではなく、実際に試してみたいというアイデアがあったからです――すると、エラーの分析や修正・改善された実装を含む、詳細で論拠のある回答が返ってきました。 会話の記録(ロシア語)をアーカイブに添付します。また、最終版のソースコードも同梱しています(中にはいくつかあり、お好きなものをお選びください)。

double SimulatePureQuantumCircuit(double &features[])
{
    const int num_states = (int)MathPow(2.0, (double)NUM_QUBITS);
    
    // 1. 状態ベクトルを作成・初期化する(決定論的進化)
    double state[];  
    ArrayResize(state, num_states);
    ArrayInitialize(state, 0.0);
    state[0] = 1.0; // 状態 |000...0>

    double next_state[];
    ArrayResize(next_state, num_states);

    // --- [進化:Ry回転弁] ---
    for(int qubit = 0; qubit < NUM_QUBITS; qubit++)
    {
        const int feature_idx = qubit % ArraySize(features);
        const double angle = MathMax(MathMin(features[feature_idx] * M_PI, M_PI), -M_PI);
        const double cos_a = MathCos(angle / 2.0);
        const double sin_a = MathSin(angle / 2.0);

        ArrayCopy(next_state, state);
        for(int i = 0; i < num_states; i++)
        {
            if((i & (1 << qubit)) == 0)
            {
                const int i1 = i | (1 << qubit);
                next_state[i]  = cos_a * state[i] - sin_a * state[i1];
                next_state[i1] = sin_a * state[i] + cos_a * state[i1];
            }
        }
        ArrayCopy(state, next_state);
    }

    // --- [進化:CZの混乱] ---
    for(int i = 0; i < NUM_QUBITS - 1; i++)
    {
        for(int j = i + 1; j < NUM_QUBITS; j++)
        {
            const double phase = M_PI / 2.0 * (features[i] * features[j]);
            if(MathAbs(phase) > M_PI / 4.0) 
            {
                for(int k = 0; k < num_states; k++)
                {
                    if(((k & (1 << i)) != 0) && ((k & (1 << j)) != 0))
                        state[k] = -state[k]; 
                }
            }
        }
    }

    // --- [真の確率の計算] ---
    double exact_probs[];
    ArrayResize(exact_probs, num_states);
    for(int i = 0; i < num_states; i++)
    {
        // 振幅の二乗は、ボルンの法則に基づく純粋な理論的確率である
        exact_probs[i] = state[i] * state[i]; 
    }

    // 2. 理想的な確率をそのまま票の重み付けに反映させる
    const double prediction = GetWeightedVote(exact_probs);
    
    return prediction; 
}

新しいソースコードについては一切検証を行っておらず、AIの主張に対しても異議を唱えていません。

この分野に詳しい方なら、評価していただけるかもしれません。

ファイル:
 

補足として、特徴の結合性を考慮した、より「包括的な」バリエーションを紹介する。この場合、特徴はペアで伝達される必要があるため、それらを1つの量子ビットの2つの異なる部分(実部と虚部)に分割する。

// グローバル設定(ご自身の取引システムに合わせて変更してください)
#define  NUM_QUBITS 3          // キュービット数(状態ベクトルのサイズ = 2^NUM_QUBITS)
#define  MIN_CONFIDENCE 0.1    // フラットをフィルタリングするための最小信頼度閾値

//+------------------------------------------------------------------+
//| セットされたビットの高速カウント(ブライアン・カーニガンの手法)      |
//+------------------------------------------------------------------+
int CountBits(int n)
{
    int count = 0;
    while(n > 0)
    {
        n &= (n - 1); 
        count++;
    }
    return count;
}

//+------------------------------------------------------------------+
//| 期待値(Expectation Value)の計算         |
//+------------------------------------------------------------------+
double GetWeightedVote(const double &state_probs[])
{
    double expected_value = 0.0;
    double total_weight = 0.0;
    const int size = ArraySize(state_probs);

    for(int i = 0; i < size; i++)
    {
        const double vote_weight = state_probs[i];
        if(vote_weight <= 0.000001) continue; 

        const int num_ones = CountBits(i);
        const double state_value = (2.0 * (double)num_ones / (double)NUM_QUBITS) - 1.0;

        expected_value += state_value * vote_weight;
        total_weight += vote_weight;
    }

    if(total_weight <= 0.0001) return 0.0;
    
    double final_prediction = expected_value / total_weight;
    if(final_prediction > 1.0)  final_prediction = 1.0;
    if(final_prediction < -1.0) final_prediction = -1.0;

    return final_prediction;
}

//+------------------------------------------------------------------+
//| 決定論的複素量子回路シミュレータ            |
//| features[][0] - 振幅パラメータ、features[][1] - 位相   |
//+------------------------------------------------------------------+
double SimulateQuantumCircuitComplex(double &features_matrix[][])
{
    const int num_states = (int)MathPow(2.0, (double)NUM_QUBITS);
    const int num_features = ArrayRange(features_matrix, 0);
    
    if(num_features == 0)
    {
        Print(「エラー:特徴行列が空です!」);
        return 0.0;
    }

    // 組み込み型 complex に基づく量子状態ベクトル
    complex state[];  
    ArrayResize(state, num_states);
    
    // システムを厳密な状態に初期化 |000...0>
    for(int i = 0; i < num_states; i++) 
    { 
        state[i].real = 0.0; 
        state[i].imag = 0.0; 
    }
    state[0].real = 1.0; // 基底状態の振幅は1である

    // ベクトルのアトミック(同時)更新用の一時バッファ
    complex next_state[];
    ArrayResize(next_state, num_states);

    // --- 1. 特徴量の複合符号化(U-Gate: Ry + Rz) ---
    for(int qubit = 0; qubit < NUM_QUBITS; qubit++)
    {
        const int feat_idx = qubit % num_features;
        
        // 入力角度を[-PI; PI]の範囲に制限する
        const double theta = MathMax(MathMin(features_matrix[feat_idx][0] * M_PI, M_PI), -M_PI); // Ry用
        const double phi   = MathMax(MathMin(features_matrix[feat_idx][1] * M_PI, M_PI), -M_PI); // Rzの場合

        const double cos_t = MathCos(theta / 2.0);
        const double sin_t = MathSin(theta / 2.0);
        
        // 位相シフトを表すオイラーの指数関数:e^(i*phi) = cos(phi) + i*sin(phi)
        complex e_phase;
        e_phase.real = MathCos(phi);
        e_phase.imag = MathSin(phi);

        ArrayCopy(next_state, state);

        for(int i = 0; i < num_states; i++)
        {
            if((i & (1 << qubit)) == 0)
            {
                const int i1 = i | (1 << qubit);
                
                // 回転弁の総合行列 U(theta, phi):
                // [   cos(θ/2)      ,  -sin(θ/2)           ]
                // [ sin(theta/2)*e^(i*phi),   cos(theta/2)*e^(i*phi) ]
                
                // ターゲットビット = 0 の場合の計算
                next_state[i].real = cos_t * state[i].real - sin_t * state[i1].real;
                next_state[i].imag = cos_t * state[i].imag - sin_t * state[i1].imag;

                // ターゲットビット=1の場合の計算(位相シフト e^i*phi を考慮)
                complex temp_i1;
                temp_i1.real = sin_t * state[i].real + cos_t * state[i1].real;
                temp_i1.imag = sin_t * state[i].imag + cos_t * state[i1].imag;
                
                // MQL5のネイティブ複素乗算を用いて位相シフトを適用する
                next_state[i1] = temp_i1 * e_phase;
            }
        }
        ArrayCopy(state, next_state);
    }

    // --- 2. 公正な複合量子エンタングルメント(Controlled-Phase Gate) ---
    for(int i = 0; i < NUM_QUBITS - 1; i++)
    {
        for(int j = i + 1; j < NUM_QUBITS; j++)
        {
            const int idx_i = i % num_features;
            const int idx_j = j % num_features;
            
            // 相互に関連する2つのパラメータの複素位相を絡み合わせる
            const double cross_phase = M_PI / 2.0 * (features_matrix[idx_i][0] * features_matrix[idx_j][1]);
            
            complex cz_gate;
            cz_gate.real = MathCos(cross_phase);
            cz_gate.imag = MathSin(cross_phase);

            for(int k = 0; k < num_states; k++)
            {
                // 両方のキュービットが状態 1 にある場合、それらの共通の複素位相を滑らかに回転させる
                if(((k & (1 << i)) != 0) && ((k & (1 << j)) != 0))
                {
                    state[k] = state[k] * cz_gate; 
                }
            }
        }
    }

    // --- 3. 正確な理論確率の算出(決定論的ステップ) ---
    double exact_probs[];
    ArrayResize(exact_probs, num_states);
    
    for(int i = 0; i < num_states; i++)
    {
        // ボルンの法則によれば、確率 P = |ψ|² = real² + imag²
        exact_probs[i] = (state[i].real * state[i].real) + (state[i].imag * state[i].imag);
    }

    // --- 4. 最終予測の取得 ---
    const double prediction = GetWeightedVote(exact_probs);
    const double confidence = MathAbs(prediction);

    if(confidence < MIN_CONFIDENCE)
    {
        return 0.0; // 量子チェーンの観点から見ると、市場は横ばい/不透明な状況にある
    }

    return prediction;
}
関連するパラメータを伝達するには、2次元(2)の行列 features[][] を使用するのが最も便利です。ここで:
  • features[i][0] — 振幅パラメータ(実部回転角(Ry)を指定する)。
  • features[i][1] — 位相特徴(複素回転角(Rz)を指定する)。
例えば、呼び出し側のコードは、[価格変動;出来高変動] または [RSIの水準;ATRの現在のボラティリティ] といったペアを送信することができます