股票量化軟件:赫茲量化中選擇一個(gè)交易平臺(tái)或經(jīng)紀(jì)商
在客戶端中創(chuàng)建數(shù)字濾波器的常用解決方案
我們剛剛討論的指標(biāo)是解決數(shù)字信號(hào)濾波這一普遍問題的一個(gè)變體。要是有一個(gè)代表常用解決方案、允許僅使用一個(gè)指標(biāo)構(gòu)建任何數(shù)字濾波器的指標(biāo)就好了。對(duì)于 赫茲量化 客戶端而言,這個(gè)問題在很久以前已使用 Sergei Ilyuhin 提供的 DF.dll 模塊解決。因此,在赫茲量化 中我們可以用它來輕松地解決問題。在該模塊中,我們引入了 DigitalFilter() 函數(shù):
DigitalFilter(int FType, int P1, int D1, int A1, int P2, int D2, int A2, double Ripple, int Delay, double& array[]);
它允許您將數(shù)字濾波器系數(shù)作為 array[] 數(shù)組接收。函數(shù)使用 reference("&" 標(biāo)記在該數(shù)組中位于此變量類型的聲明之后)將數(shù)字濾波器系數(shù)寫入此大小為 1500 的數(shù)組中。函數(shù)接收十個(gè)輸入?yún)?shù)的值并返回?cái)?shù)字濾波器的大小。因此,這足以構(gòu)建通用數(shù)字濾波器。整個(gè)問題歸結(jié)于基于全局層面在現(xiàn)有指標(biāo)中組織 DLL 輸入,在指標(biāo)初始化代碼塊中獲取系數(shù)數(shù)組,并基于這些系數(shù)在 OnCalculate() 中運(yùn)行濾波器的通用計(jì)算。DigitalFilter() 函數(shù)的輸入變量應(yīng)置于指標(biāo)的輸入變量中。我們現(xiàn)在就開始。
導(dǎo)入 DF.dll 文件不會(huì)帶來任何困難。它只有三行代碼:
//---- 引入DLL #import "DF.dll" int DigitalFilter(int FType, int P1, int D1, int A1, int P2, int D2, int A2, double Ripple, int Delay, double& array[]); #import
之后,將 DigitalFilter() 函數(shù)的所有外部變量作為指標(biāo)的輸入變量:
//---- 指標(biāo)的輸入?yún)?shù) input FType_ FType=LPF; ? ? //濾波器類型 ? ? ? ? ? ? ? ? ? ? ? ? ? ?//0 - 低通濾波器 (FATL/SATL/KGLP),1 - 高通濾波器 (KGHP), ? ? ? ? ? ? ? ? ? ? ? ? ? ?//2 - 帶通濾波器 (RBCI / KGBP),3 - 帶阻濾波器 (KGBS) input int ? ?P1 = 28; ? ? ? //截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) input int ? ?D1 = 19; ? ? ? //穩(wěn)態(tài)過程截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) input int ? ?A1 = 40; ? ? ? //延時(shí)帶1的衰減,單位dB input int ? ?P2 = 0; ? ? ? ?//截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) input int ? ?D2 = 0; ? ? ? ?//穩(wěn)態(tài)過程截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) input int ? ?A2 = 0; ? ? ? ?//延時(shí)帶2的衰減,單位dB input int ? ?Delay=0; ? ? ? //延遲,以柱形個(gè)數(shù)計(jì) input double Ripple=0.08; ? //帶寬中的波動(dòng),單位dB input int ? ?FILTERShift=0; //移動(dòng)平均的水平方向偏移,以柱形計(jì)
在全局層面,我們將聲明 FILTERPeriod 變量但不對(duì)其進(jìn)行初始化:
//---- 聲明并初始化一個(gè)變量來存儲(chǔ)已計(jì)算的柱形的數(shù)量 int FILTERPeriod;
在全局層面,我們將聲明一個(gè)動(dòng)態(tài)數(shù)組用于存儲(chǔ)濾波器系數(shù):
//---- 聲明動(dòng)態(tài)數(shù)組, // ? ? 將用作指標(biāo)的緩存 double FILTERTable[];
現(xiàn)在,我們考慮 OnInit() 函數(shù)的代碼塊。將 FILTERTable[] 數(shù)組用作 DigitalFilter() 函數(shù)的參數(shù)并不太合乎邏輯。為此,我們需要使數(shù)組的大小能容納 1500 個(gè)元素,但其中僅 100 - 200 個(gè)元素會(huì)在 OnCalculate() 函數(shù)塊中用到。在此情形下,我們?cè)?OnInit() 函數(shù)中使用局部聲明的 Array[1500] 數(shù)組反而會(huì)更好。來自該數(shù)組的必要數(shù)據(jù)量將被寫入 FILTERTable[] 數(shù)組。在從 OnInit() 函數(shù)退出后,大規(guī)模的 Array[] 數(shù)組將被銷毀,而必要數(shù)據(jù)將保留在 FILTERTable[] 數(shù)組中,其大小等于 FILTERPeriod 數(shù)字濾波器的長(zhǎng)度。下面是用于此目的的代碼變體:
//---- 計(jì)算數(shù)字濾波器的系數(shù)并確定FILTERTable[] 緩存的大小 ? double Array[1500]; ? FILTERPeriod=DigitalFilter(FType,P1,D1,A1,P2,D2,A2,Ripple,Delay,Array); //---- ?改變數(shù)字濾波器所需系數(shù)的FILTERTable[]緩存的大小 ? if(FILTERPeriod<=0) ? ? { ? ? ?Print("Input parameters are incorrect. Indicator can't operate!"); ? ? ?return; ? ? } //---- 將大小為1500的臨時(shí)數(shù)組中的數(shù)據(jù),復(fù)制到大小為FILTERPeriod的主數(shù)組中 ? ArrayCopy(FILTERTable,Array,0,0,FILTERPeriod);
在 OnCalculate() 函數(shù)中,濾波器計(jì)算的代碼十分簡(jiǎn)單:
? ? ?//---- 數(shù)字濾波器計(jì)算公式 ? ? ?FILTER=0.0; ? ? ?for(iii = 0; iii<FILTERPeriod; iii++) ? ? ? ? FILTER+= FILTERTable[iii] * price[bar - iii];
該指標(biāo)代碼的最終版本在 DFilter_en.mq5 文件中給出。我們可以對(duì)指標(biāo)的接口稍作修改。事實(shí)上,指標(biāo)輸入變量的取值范圍為 0-3。
input int FType = 0; //濾波器類型 ? ? ? ? ? ? ? ? ? ? //0 - 低通濾波器 (FATL/SATL/KGLP),1 - 高通濾波器 (KGHP),2 - 帶通濾波器 (RBCI / KGBP),3 - 帶阻濾波器 (KGBS)
這些值如果作為濾波器的名稱而不是以數(shù)字形式出現(xiàn),要更容易理解:0 - 低通濾波器 (FATL/SATL/KGLP),1 - 高通濾波器 (KGHP),2 - 帶通濾波器 (RBCI/KGBP),3 - 帶阻濾波器 (KGBS)。對(duì)于這種情況,MQL5 中存在名為枚舉的特殊變量類型。在我們的示例中,我們需要在指標(biāo)的輸入?yún)?shù)前聲明和初始化枚舉:
//---- 聲明和初始化數(shù)字濾波器類型 enum FType_ //濾波器類型 ?{ ? LPF, //低通濾波器 (FATL/SATL/KGLP) ? HPF, //高通濾波器 (KGHP) ? BPF, //帶通濾波器 (RBCI/KGBP) ? BSF, //帶阻濾波器 (KGBS) ?};
之后,我們需要在指標(biāo)外部參數(shù)的聲明中替換使用變量的類型:
input FType_ FType = LPF; //濾波器類型
如此一來,在指標(biāo)的對(duì)話框中選擇該參數(shù)的值的情形如下圖所示:

編輯切換為居中
與枚舉聲明一樣,命名常量后跟單行注釋,然后它們被選作輸入?yún)?shù)?,F(xiàn)在,我們有了通用數(shù)字濾波器源代碼的最終版本:
//+------------------------------------------------------------------+ //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?ProjectName | //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?Copyright 2010, CompanyName | //| ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? http://www.companyname.net | //+------------------------------------------------------------------+ /* * <<< METATRADER 5 的數(shù)字濾波器 >>> * * * DF.dll 文件應(yīng)放在 "\MetaTrader 5\MQL5\Libraries\" 文件夾下。 * DF.dll 需要另外三個(gè)DLLs,包括一個(gè)數(shù)學(xué)模塊 * 處理 - bdsp.dll, lapack.dll, mkl_support.dll. * 對(duì)于Windows 32-位操作系統(tǒng),這些 DLLs 必須安裝到 "C:\Windows\System32\" 文件夾下 * 或者對(duì)于Windows 64-位操作系統(tǒng),安裝到 "C:\Windows\SysWOW64\" 文件夾下。 * * * 在使用前,請(qǐng)確保: * * 1. 終端設(shè)置中“允許加載DLL” 的選項(xiàng)已啟用 * ? ?(Tools->Options->Expert Advisors tab). * 2. 在"C:\Windows\System32\" 或"C:\Windows\SysWOW64\" 文件夾下 * ? ?Bdsp.dll, lapack.dll and mkl_support.dll 輔助數(shù)學(xué)庫存在。 * * 輸入?yún)?shù)的描述: * * Ftype ?- 濾波器類型:0 - 低通濾波器 (FATL/SATL/KGLP), 1 - 高通濾波器 (KGHP), * ? ? ? ? ?2 - 帶通濾波器 (RBCI / KGBP), 3 - 帶阻濾波器 (KGBS) * P1 ? ? - 截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) * D1 ? ? - 穩(wěn)態(tài)過程截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) * A1 ? ? - 延時(shí)帶1的衰減,單位dB * P2 ? ? - 截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) * D2 ? ? - 穩(wěn)態(tài)過程截?cái)嘀芷?,以柱形個(gè)數(shù)計(jì) * A2 ? ? - 延時(shí)帶2的衰減,單位dB * Ripple - 帶寬, 單位dB * Delay ?- 延遲,以柱形計(jì) * * 對(duì)于低通濾波器和HPF,P2, D2, A2 的值可忽略 * * 條件: * 低通濾波器: ? ? ? ? ? ? ? ? ? ? ?P1>D1 * 高通濾波器: ? ? ? ? ? ? ? ? ? ? ?P1<D1 * 帶通濾波器和帶阻濾波器:D2>P2>P1>D1 */