常用技術指標 MQL5 完整實作:RSI、MACD、布林通道

📌 本文重點
學習如何在 MQL5 中正確使用 RSI、MACD、布林通道三大技術指標:句柄建立、數值讀取、訊號判斷,以及三指標組合過濾策略。

指標使用的標準流程

所有 MQL5 內建指標都遵循相同的三步驟:建立句柄 → 複製數據 → 釋放句柄

RSI(相對強弱指數)

int g_rsiHandle = INVALID_HANDLE;

int OnInit()
{
    // 建立 RSI 句柄(14期,使用收盤價)
    g_rsiHandle = iRSI(_Symbol, _Period, 14, PRICE_CLOSE);
    if (g_rsiHandle == INVALID_HANDLE) return INIT_FAILED;
    return INIT_SUCCEEDED;
}

void OnDeinit(const int reason) { IndicatorRelease(g_rsiHandle); }

// 取得 RSI 值並判斷訊號
void CheckRSI()
{
    double rsi[3];
    ArraySetAsSeries(rsi, true);
    if (CopyBuffer(g_rsiHandle, 0, 0, 3, rsi) < 3) return;

    // rsi[0]=當前(未完成), rsi[1]=前一根(完成), rsi[2]=前兩根
    Print("RSI[1]=", rsi[1], " RSI[2]=", rsi[2]);

    // 超賣反彈訊號:RSI 從低於30回升至30以上
    if (rsi[2] < 30 && rsi[1] >= 30) Print("RSI 超賣回升!做多機會");

    // 超買回落訊號:RSI 從高於70回落至70以下
    if (rsi[2] > 70 && rsi[1] <= 70) Print("RSI 超買回落!做空機會");
}

MACD(移動平均收斂發散)

int g_macdHandle = INVALID_HANDLE;

int OnInit()
{
    // MACD(12, 26, 9),標準參數
    g_macdHandle = iMACD(_Symbol, _Period, 12, 26, 9, PRICE_CLOSE);
    if (g_macdHandle == INVALID_HANDLE) return INIT_FAILED;
    return INIT_SUCCEEDED;
}

void CheckMACD()
{
    double macdLine[3], signalLine[3];
    ArraySetAsSeries(macdLine,   true);
    ArraySetAsSeries(signalLine, true);

    // Buffer 0 = MACD 線, Buffer 1 = 信號線
    if (CopyBuffer(g_macdHandle, 0, 0, 3, macdLine)   < 3) return;
    if (CopyBuffer(g_macdHandle, 1, 0, 3, signalLine) < 3) return;

    // 柱狀圖 = MACD線 - 信號線
    double hist1 = macdLine[1] - signalLine[1];
    double hist2 = macdLine[2] - signalLine[2];

    // 金叉(MACD線從下穿越信號線)
    if (macdLine[2] <= signalLine[2] && macdLine[1] > signalLine[1])
        Print("MACD 金叉!做多");

    // 死叉(MACD線從上穿越信號線)
    if (macdLine[2] >= signalLine[2] && macdLine[1] < signalLine[1])
        Print("MACD 死叉!做空");

    // 柱狀圖轉正(動能由弱轉強)
    if (hist2 < 0 && hist1 >= 0) Print("MACD 柱狀圖轉正");
}

布林通道(Bollinger Bands)

int g_bbHandle = INVALID_HANDLE;

int OnInit()
{
    // 布林通道(20, 2.0),使用收盤價
    g_bbHandle = iBands(_Symbol, _Period, 20, 0, 2.0, PRICE_CLOSE);
    if (g_bbHandle == INVALID_HANDLE) return INIT_FAILED;
    return INIT_SUCCEEDED;
}

void CheckBollinger()
{
    double upper[2], middle[2], lower[2];
    ArraySetAsSeries(upper,  true);
    ArraySetAsSeries(middle, true);
    ArraySetAsSeries(lower,  true);

    // Buffer 0=中軌(SMA), 1=上軌, 2=下軌
    if (CopyBuffer(g_bbHandle, 0, 0, 2, middle) < 2) return;
    if (CopyBuffer(g_bbHandle, 1, 0, 2, upper)  < 2) return;
    if (CopyBuffer(g_bbHandle, 2, 0, 2, lower)  < 2) return;

    double close1 = iClose(_Symbol, _Period, 1);
    double close2 = iClose(_Symbol, _Period, 2);

    // 下軌反彈:收盤價從下軌以下回到上方
    if (close2 < lower[1] && close1 >= lower[0]) Print("布林下軌反彈!做多");

    // 上軌回落:收盤價從上軌以上回到下方
    if (close2 > upper[1] && close1 <= upper[0]) Print("布林上軌回落!做空");

    // 布林通道寬度(衡量波動率)
    double bandwidth = (upper[1] - lower[1]) / middle[1] * 100;
    if (bandwidth < 5.0) Print("布林通道收縮(波動率低),可能即將突破");
}

三指標組合過濾策略

void OnTick()
{
    static datetime lastBarTime = 0;
    datetime curTime = iTime(_Symbol, _Period, 0);
    if (curTime == lastBarTime) return;
    lastBarTime = curTime;

    // 讀取三個指標
    double rsi[2], macd[2], sig[2], upper[2], lower[2], mid[2];
    ArraySetAsSeries(rsi, true);
    ArraySetAsSeries(macd, true);
    ArraySetAsSeries(sig, true);
    ArraySetAsSeries(upper, true);
    ArraySetAsSeries(lower, true);
    ArraySetAsSeries(mid, true);

    if (CopyBuffer(g_rsiHandle,  0, 0, 2, rsi)    < 2) return;
    if (CopyBuffer(g_macdHandle, 0, 0, 2, macd)   < 2) return;
    if (CopyBuffer(g_macdHandle, 1, 0, 2, sig)    < 2) return;
    if (CopyBuffer(g_bbHandle,   1, 0, 2, upper)  < 2) return;
    if (CopyBuffer(g_bbHandle,   2, 0, 2, lower)  < 2) return;
    if (CopyBuffer(g_bbHandle,   0, 0, 2, mid)    < 2) return;

    double close = iClose(_Symbol, _Period, 1);

    // 多單條件:RSI 超賣 + MACD 金叉 + 價格在布林下軌附近
    bool buyCondition = rsi[1] < 35 &&
                        macd[1] > sig[1] &&
                        close < mid[1];

    // 空單條件:RSI 超買 + MACD 死叉 + 價格在布林上軌附近
    bool sellCondition = rsi[1] > 65 &&
                         macd[1] < sig[1] &&
                         close > mid[1];

    if (buyCondition)  Print("三指標共振!做多信號");
    if (sellCondition) Print("三指標共振!做空信號");
}

本文由 James Lee 撰寫。內容僅供教育目的,不構成投資建議。

Similar Posts

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *