量化交易軟件:交易策略中的模糊邏輯
交易者經(jīng)常想知道如何通過機(jī)器學(xué)習(xí)來改善交易系統(tǒng)或創(chuàng)建新的交易系統(tǒng)。盡管有大量出版物發(fā)表, 依然未能找到一個(gè)不借助計(jì)算機(jī)輔助計(jì)算來建立簡單、直觀分析模型的方法。模糊邏輯是機(jī)器學(xué)習(xí)世界的一個(gè)窗口。結(jié)合遺傳算法, 它能夠擴(kuò)展創(chuàng)建自學(xué)習(xí)或易于優(yōu)化的交易系統(tǒng)的能力。同時(shí), 模糊邏輯是直觀的, 因?yàn)樗谀:?(虛化的) 條例中封裝了清晰的數(shù)值信息, 就像一個(gè)人在思考過程中所做的那樣。

編輯切換為居中
此處是一個(gè)例子。在清晰的邏輯層面, 運(yùn)動(dòng)車輛的速度由測(cè)量設(shè)備判定: 例如, 60 千米/小時(shí)。但一個(gè)沒有測(cè)量設(shè)備且漫不經(jīng)心的觀察者只能依靠他的經(jīng)驗(yàn)或認(rèn)知基礎(chǔ)來粗略地估計(jì)車輛的速度。例如, 已知車輛可以快速行駛, 而 "快速" 大約定義為 100 千米/小時(shí)以上。同樣已知, 一輛車也可慢速運(yùn)動(dòng), 即 5-10 千米/小時(shí)。最后, 如果相應(yīng)的車輛以中等速率增加, 則目視評(píng)估速度為平均 (約 60 千米/小時(shí))。因此, 可以用四種不同的表達(dá)式來表征 60 千米/小時(shí):
平均速度;
速度接近平均水平;
比平均快;
以及最后, 比平均慢。
這就是信息如何被封裝在人的意識(shí)中, 令他只需掌握當(dāng)前必要的信息, 例如: "如果車輛行駛速度 不是很快, 我是否有時(shí)間穿過馬路?"。在做出任何具體的決定之前: "跑過馬路或讓車先行", 一次性地深入思考所有事情會(huì)迫使一個(gè)人花費(fèi)大量的時(shí)間和精力。與此同時(shí), 徹底研究當(dāng)前形勢(shì), 而其也許今后永遠(yuǎn)不會(huì)重現(xiàn), 只會(huì)有類似的輪廓。在機(jī)器學(xué)習(xí)中, 這種情況被稱為過度擬合。
本文不會(huì)深入到模糊邏輯理論。有關(guān)此主題的信息可以在互聯(lián)網(wǎng)和 MQL5 網(wǎng)站 上獲得。赫茲量化交易現(xiàn)在立即開始實(shí)踐, 用理論節(jié)選和奇妙的事實(shí)來解釋。
為了構(gòu)建模型, 使用標(biāo)準(zhǔn)赫茲量化交易終端軟件包中提供的 模糊邏輯 函數(shù)庫。
成果為現(xiàn)成的是基于模糊邏輯的智能交易系統(tǒng), 可作為建立定制系統(tǒng)的一個(gè)例子。
創(chuàng)建交易系統(tǒng)的原型
赫茲量化交易繼續(xù)創(chuàng)建 清晰的 交易邏輯, 這將作為進(jìn)一步研究的基礎(chǔ)。然后可以比較兩個(gè)相同的系統(tǒng), 其中第二個(gè)將運(yùn)用模糊邏輯。
將使用 3 個(gè)不同周期的 RSI 振蕩器作為基礎(chǔ):
hnd1 = iRSI(_Symbol,0,9,PRICE_CLOSE); hnd2 = iRSI(_Symbol,0,14,PRICE_CLOSE); hnd3 = iRSI(_Symbol,0,21,PRICE_CLOSE);
赫茲量化交易將信號(hào)的清晰條件公式化, 并在函數(shù)中定義它們:
double CalculateSignal() { double res =0.5; CopyBuffer(hnd1,0,0,1,arr1); CopyBuffer(hnd2,0,0,1,arr2); CopyBuffer(hnd3,0,0,1,arr3); if(arr1[0]>70 && arr2[0]>70 && arr3[0]>70) res=1.0; ? ? ? ? ? ? ? ? ? ?// 如果所有指標(biāo)都處于超買區(qū)域, 賣出 if(arr1[0]<30 && arr2[0]<30 && arr3[0]<30) res=0.0; ? ? ? ? ? ? ? ? ? ?// 如果所有指標(biāo)都處于超賣區(qū)域, 買入 if(arr1[0]<30 && arr2[0]<30 && arr3[0]>70) res=0.5; ? ? ? ? ? ? ? ? ? ?// 如果 2 個(gè)超賣, 1 個(gè)超買, 則無信號(hào) if(arr1[0]<30 && arr2[0]>70 && arr3[0]<30) res=0.5; if(arr1[0]>70 && arr2[0]<30 && arr3[0]<30) res=0.5; if(arr1[0]>70 && arr2[0]>70 && arr3[0]<30) res=0.5; ? ? ? ? ? ? ? ? ? ?// 如果 2 個(gè)超買, 1 個(gè)超賣, 則無信號(hào) if(arr1[0]>70 && arr2[0]<30 && arr3[0]>70) res=0.5; if(arr1[0]<30 && arr2[0]>70 && arr3[0]>70) res=0.5; if(arr1[0]<30 && arr2[0]<30 && (arr3[0]>40 && arr3[0]<60)) res=0.0; ? ?// 如果 2 個(gè)超賣, 第 3 個(gè)范圍在 40 - 60, 則為買入信號(hào) if(arr1[0]<30 && (arr2[0]>40 && arr2[0]<60) && arr3[0]<30) res=0.0; if((arr1[0]>40 && arr1[0]<60) && arr2[0]<30 && arr3[0]<30) res=0.0; if(arr1[0]>70 && arr2[0]>70 && (arr3[0]>40 && arr3[0]<60)) res=1.0; ? ?// 如果 2 個(gè)超買, 第 3 個(gè)范圍在 40 - 60, 則為賣出信號(hào) if(arr1[0]>70 && (arr2[0]>40 && arr2[0]<60) && arr3[0]>70) res=1.0; if((arr1[0]>40 && arr1[0]<60) && arr2[0]>70 && arr3[0]>70) res=1.0; return(res); }
下一步, 赫茲量化交易編寫所有其它的服務(wù)函數(shù), 針對(duì) EURUSD, 時(shí)間幀 М15 和 М5, 從 2017 年初開始測(cè)試 (完整的 智能系統(tǒng)代碼附于文章末尾):

編輯切換為居中

編輯切換為居中
盡管已經(jīng)定義了三個(gè)指標(biāo)組合的清晰條件, 這些條件是合乎邏輯且一致的, 但這種方法過于簡單和僵化。平均而言, 這個(gè)系統(tǒng)在 8 個(gè)月的時(shí)間內(nèi)既沒虧損也沒賺錢。為了賺取收益, 有必要遍歷多種條件組合, 并可能添加更多的振蕩器。但這里沒留下太多的優(yōu)化控件, 因?yàn)闂l件設(shè)置極端精確。
赫茲量化交易嘗試運(yùn)用模糊邏輯來虛化交易系統(tǒng)盈利的條件。
創(chuàng)建一個(gè)模糊邏輯模型
首先, 必須包含模糊函數(shù)庫。準(zhǔn)確地說, 使用兩種可用的模糊邏輯模型之一 - Mamdani 或 Sugeno。它們之間的區(qū)別在于, Sugeno 無需創(chuàng)建模糊項(xiàng)集合形式的輸出變量即可輸出一個(gè)線性模型, 而 Mamdani 提供這個(gè)元素。由于這篇文章是為模糊交易者撰寫的, 所以將使用 Mamdani。但這并不意味著 Sugeno 模型不適用于某些特定的任務(wù): 依據(jù)對(duì)模糊邏輯的基本理解, 進(jìn)行實(shí)驗(yàn)始終是可能的且必要的。
#include <Math\Fuzzy\MamdaniFuzzySystem.mqh> CMamdaniFuzzySystem *OurFuzzy=new CMamdaniFuzzySystem();
函數(shù)庫已包含在內(nèi), 聲明 Mamdani 類的引用。這就是開始所需的一切。
現(xiàn)在赫茲量化交易來研究構(gòu)建模糊推理的主要階段。它在模糊建模系統(tǒng)中占據(jù)著中心地位。模糊推理過程是運(yùn)用模糊邏輯的基本操作, 基于模糊假設(shè)獲得模糊結(jié)論的具體過程或算法。
模糊推理有 7 個(gè)階段。
判斷模糊推理系統(tǒng)的結(jié)構(gòu)。
輸入和輸出的數(shù)量, 以及成員函數(shù)在設(shè)計(jì)階段即已定義。在赫茲量化交易的案例中, 會(huì)有 4 個(gè)輸入, 1 個(gè)輸出, 每個(gè)輸入都有 3 個(gè)成員函數(shù)。
形成模糊推理系統(tǒng)的規(guī)則基準(zhǔn)。
在開發(fā)過程中, 赫茲量化交易基于交易系統(tǒng)的專業(yè)判斷, 創(chuàng)建模糊推理的自定義規(guī)則。
輸入變量的模糊化。
在模糊推理系統(tǒng)輸入變量的數(shù)值, 與語言變量對(duì)應(yīng)項(xiàng)的成員函數(shù)的值之間設(shè)置對(duì)應(yīng)關(guān)系。
聚合
判斷模糊推理系統(tǒng)每條規(guī)則的條件真實(shí)度的過程。
激活
查找構(gòu)成所有模糊生產(chǎn)規(guī)則的核心后果的每個(gè)基本命題 (小節(jié)) 的真實(shí)度的過程。
積累
為每個(gè)輸出的語言變量查找成員函數(shù)的過程。
去模糊化
從輸出的語言變量的成員函數(shù)過渡為清晰 (數(shù)字) 值的過程。輸出值將在從 0 到 1 范圍內(nèi)。
應(yīng)該指出的是, 只有第 1 點(diǎn)和第 2 點(diǎn)需要執(zhí)行, 其它所有的操作都將由系統(tǒng)完成, 無需干預(yù)。若對(duì)模糊邏輯操作所有階段的細(xì)微之處感興趣的人可在 這里 找到更多細(xì)節(jié)。
判斷模糊推理系統(tǒng)的結(jié)構(gòu)
赫茲量化交易繼續(xù)創(chuàng)建模型。定義三個(gè)輸入和一個(gè)輸出的對(duì)象, 以及輔助字典對(duì)象, 以便于運(yùn)用邏輯操作:
CFuzzyVariable *firstInput=new CFuzzyVariable("rsi1",0.0,1.0); CFuzzyVariable *secondInput=new CFuzzyVariable("rsi2",0.0,1.0); CFuzzyVariable *thirdInput=new CFuzzyVariable("rsi3",0.0,1.0); CFuzzyVariable *fuzzyOut=new CFuzzyVariable("out",0.0,1.0); CDictionary_Obj_Double *firstTerm=new CDictionary_Obj_Double; CDictionary_Obj_Double *secondTerm=new CDictionary_Obj_Double; CDictionary_Obj_Double *thirdTerm=new CDictionary_Obj_Double; CDictionary_Obj_Double *Output;
三個(gè)不同周期的 RSI 將被用作輸入。由于 RSI 振蕩器始終在 0-100 范圍內(nèi), 因此必須為其創(chuàng)建一個(gè)具有相同維度的變量。但為方便起見, 指標(biāo)值將被常規(guī)化到 0-1 的范圍。請(qǐng)記住, 所創(chuàng)建變量的維度必須等于輸入向量的維度, 即它必須包含所有的值。輸出也設(shè)置為從 0 到 1 的范圍。
根據(jù)模糊邏輯創(chuàng)建的第 1 點(diǎn), 還需要定義和配置成員函數(shù)。這將在 OnInit() 事件處理程序中完成:
firstInput.Terms().Add(new CFuzzyTerm("buy", new CZ_ShapedMembershipFunction(0.0,0.6))); firstInput.Terms().Add(new CFuzzyTerm("neutral", new CNormalMembershipFunction(0.5, 0.2))); firstInput.Terms().Add(new CFuzzyTerm("sell", new CS_ShapedMembershipFunction(0.4,1.0))); OurFuzzy.Input().Add(firstInput); ? secondInput.Terms().Add(new CFuzzyTerm("buy", new CZ_ShapedMembershipFunction(0.0,0.6))); secondInput.Terms().Add(new CFuzzyTerm("neutral", new CNormalMembershipFunction(0.5, 0.2))); secondInput.Terms().Add(new CFuzzyTerm("sell", new CS_ShapedMembershipFunction(0.4,1.0))); OurFuzzy.Input().Add(secondInput); ? thirdInput.Terms().Add(new CFuzzyTerm("buy", new CZ_ShapedMembershipFunction(0.0,0.6))); thirdInput.Terms().Add(new CFuzzyTerm("neutral", new CNormalMembershipFunction(0.5, 0.2))); thirdInput.Terms().Add(new CFuzzyTerm("sell", new CS_ShapedMembershipFunction(0.4,1.0))); OurFuzzy.Input().Add(thirdInput); ? fuzzyOut.Terms().Add(new CFuzzyTerm("buy", new CZ_ShapedMembershipFunction(0.0,0.6))); fuzzyOut.Terms().Add(new CFuzzyTerm("neutral", new CNormalMembershipFunction(Gposition, Gsigma))); fuzzyOut.Terms().Add(new CFuzzyTerm("sell", new CS_ShapedMembershipFunction(0.4,1.0))); OurFuzzy.Output().Add(fuzzyOut);
現(xiàn)在我們看看成員函數(shù)是什么樣, 以及它的用途是什么。
已經(jīng)為每個(gè)輸入 (和一個(gè)輸出) 變量創(chuàng)建了三個(gè)條例: "買入", "中性", "賣出", 每個(gè)都有自己的成員函數(shù)。換言之, 振蕩器值現(xiàn)在可以被劃分到 3 個(gè)模糊組, 并且可以使用成員函數(shù)為每個(gè)組分配一定范圍的值。用模糊邏輯的語言來說, 已經(jīng)創(chuàng)建了 4 個(gè)條例集, 每個(gè)條例集有 3 個(gè)條例。為了描繪上述情況, 赫茲量化交易將編寫一個(gè)簡單的腳本, 用于條例及其成員函數(shù)的可視化:
//+------------------------------------------------------------------+ //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?Our MembershipFunctions.mq5 | //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 版權(quán)所有 2016, MetaQuotes 軟件公司| //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? https://www.mql5.com | //+------------------------------------------------------------------+ #include <Math\Fuzzy\membershipfunction.mqh> #include <Graphics\Graphic.mqh> //--- 創(chuàng)建成員函數(shù) CZ_ShapedMembershipFunction func2(0.0, 0.6); CNormalMembershipFunction func1(0.5, 0.2); CS_ShapedMembershipFunction func3(0.4, 1.0); //--- 創(chuàng)建成員函數(shù)的包裝 double NormalMembershipFunction1(double x) { return(func1.GetValue(x)); } double ZShapedMembershipFunction(double x) { return(func2.GetValue(x)); } double SShapedMembershipFunction(double x) { return(func3.GetValue(x)); } //+------------------------------------------------------------------+ //| 腳本程序啟動(dòng)函數(shù) ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?| //+------------------------------------------------------------------+ void OnStart() ?{ //--- 創(chuàng)建圖形 ? CGraphic graphic; ? if(!graphic.Create(0,"Our MembershipFunctions",0,30,30,780,380)) ? ? { ? ? ?graphic.Attach(0,"Our MembershipFunctions"); ? ? } ? graphic.HistoryNameWidth(70); ? graphic.BackgroundMain("Our MembershipFunctions"); ? graphic.BackgroundMainSize(16); //--- 創(chuàng)建曲線 ? graphic.CurveAdd(NormalMembershipFunction1,0.0,1.0,0.01,CURVE_LINES,"[0.5, 0.2]"); ? graphic.CurveAdd(ZShapedMembershipFunction,0.0,1.0,0.01,CURVE_LINES,"[0.0, 0.6]"); ? graphic.CurveAdd(SShapedMembershipFunction,0.0,1.0,0.01,CURVE_LINES,"[0.4, 1.0]"); //--- 設(shè)置 X 軸屬性 ? graphic.XAxis().AutoScale(false); ? graphic.XAxis().Min(0.0); ? graphic.XAxis().Max(1.0); ? graphic.XAxis().DefaultStep(0.1); //--- 設(shè)置 Y 軸屬性 ? graphic.YAxis().AutoScale(false); ? graphic.YAxis().Min(0.0); ? graphic.YAxis().Max(1.1); ? graphic.YAxis().DefaultStep(0.1); //--- 繪圖 ? graphic.CurvePlotAll(); ? graphic.Update(); ?}
在圖表上運(yùn)行腳本:

編輯切換為居中
所選的這些成員函數(shù), 是因?yàn)樗鼈冎挥?2 個(gè)可優(yōu)化的輸入?yún)?shù) (這將在稍后的系統(tǒng)測(cè)試階段完成)。它們也很好地描述了這個(gè)系統(tǒng)的極值和中心位置。您可以應(yīng)用模糊函數(shù)庫中 可用的 任何成員函數(shù)。