股票量化软件:赫兹量化中选择一个交易平台或经纪商

在客户端中创建数字滤波器的常用解决方案

我们刚刚讨论的指标是解决数字信号滤波这一普遍问题的一个变体。要是有一个代表常用解决方案、允许仅使用一个指标构建任何数字滤波器的指标就好了。对于 赫兹量化 客户端而言,这个问题在很久以前已使用 Sergei Ilyuhin 提供的 DF.dll 模块解决。因此,在赫兹量化 中我们可以用它来轻松地解决问题。在该模块中,我们引入了 DigitalFilter() 函数:

 
 

DigitalFilter(int FType, int P1, int D1, int A1, int P2, int D2, int A2, double Ripple, int Delay, double& array[]);

它允许您将数字滤波器系数作为 array[] 数组接收。函数使用 reference("&" 标记在该数组中位于此变量类型的声明之后)将数字滤波器系数写入此大小为 1500 的数组中。函数接收十个输入参数的值并返回数字滤波器的大小。因此,这足以构建通用数字滤波器。整个问题归结于基于全局层面在现有指标中组织 DLL 输入,在指标初始化代码块中获取系数数组,并基于这些系数在 OnCalculate() 中运行滤波器的通用计算。DigitalFilter() 函数的输入变量应置于指标的输入变量中。我们现在就开始。

导入 DF.dll 文件不会带来任何困难。它只有三行代码:

 
 

//---- 引入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() 函数的所有外部变量作为指标的输入变量:

 
 

//---- 指标的输入参数 input FType_ FType=LPF; //滤波器类型 //0 - 低通滤波器 (FATL/SATL/KGLP),1 - 高通滤波器 (KGHP), //2 - 带通滤波器 (RBCI / KGBP),3 - 带阻滤波器 (KGBS) input int P1 = 28; //截断周期1,以柱形个数计 input int D1 = 19; //稳态过程截断周期1,以柱形个数计 input int A1 = 40; //延时带1的衰减,单位dB input int P2 = 0; //截断周期2,以柱形个数计 input int D2 = 0; //稳态过程截断周期2,以柱形个数计 input int A2 = 0; //延时带2的衰减,单位dB input int Delay=0; //延迟,以柱形个数计 input double Ripple=0.08; //带宽中的波动,单位dB input int FILTERShift=0; //移动平均的水平方向偏移,以柱形计

在全局层面,我们将声明 FILTERPeriod 变量但不对其进行初始化:

 
 

//---- 声明并初始化一个变量来存储已计算的柱形的数量 int FILTERPeriod;

在全局层面,我们将声明一个动态数组用于存储滤波器系数:

 
 

//---- 声明动态数组, // 将用作指标的缓存 double FILTERTable[];

现在,我们考虑 OnInit() 函数的代码块。将 FILTERTable[] 数组用作 DigitalFilter() 函数的参数并不太合乎逻辑。为此,我们需要使数组的大小能容纳 1500 个元素,但其中仅 100 - 200 个元素会在 OnCalculate() 函数块中用到。在此情形下,我们在 OnInit() 函数中使用局部声明的 Array[1500] 数组反而会更好。来自该数组的必要数据量将被写入 FILTERTable[] 数组。在从 OnInit() 函数退出后,大规模的 Array[] 数组将被销毁,而必要数据将保留在 FILTERTable[] 数组中,其大小等于 FILTERPeriod 数字滤波器的长度。下面是用于此目的的代码变体:

 
 

//---- 计算数字滤波器的系数并确定FILTERTable[] 缓存的大小 double Array[1500]; FILTERPeriod=DigitalFilter(FType,P1,D1,A1,P2,D2,A2,Ripple,Delay,Array); //---- 改变数字滤波器所需系数的FILTERTable[]缓存的大小 if(FILTERPeriod<=0) { Print("Input parameters are incorrect. Indicator can't operate!"); return; } //---- 将大小为1500的临时数组中的数据,复制到大小为FILTERPeriod的主数组中 ArrayCopy(FILTERTable,Array,0,0,FILTERPeriod);

OnCalculate() 函数中,滤波器计算的代码十分简单:

 
 

//---- 数字滤波器计算公式 FILTER=0.0; for(iii = 0; iii<FILTERPeriod; iii++) FILTER+= FILTERTable[iii] * price[bar - iii];

该指标代码的最终版本在 DFilter_en.mq5 文件中给出。我们可以对指标的接口稍作修改。事实上,指标输入变量的取值范围为 0-3。

 
 

input int FType = 0; //滤波器类型 //0 - 低通滤波器 (FATL/SATL/KGLP),1 - 高通滤波器 (KGHP),2 - 带通滤波器 (RBCI / KGBP),3 - 带阻滤波器 (KGBS)

这些值如果作为滤波器的名称而不是以数字形式出现,要更容易理解:0 - 低通滤波器 (FATL/SATL/KGLP),1 - 高通滤波器 (KGHP),2 - 带通滤波器 (RBCI/KGBP),3 - 带阻滤波器 (KGBS)。对于这种情况,MQL5 中存在名为枚举的特殊变量类型。在我们的示例中,我们需要在指标的输入参数前声明和初始化枚举:

 
 

//---- 声明和初始化数字滤波器类型 enum FType_ //滤波器类型 { LPF, //低通滤波器 (FATL/SATL/KGLP) HPF, //高通滤波器 (KGHP) BPF, //带通滤波器 (RBCI/KGBP) BSF, //带阻滤波器 (KGBS) };

之后,我们需要在指标外部参数的声明中替换使用变量的类型:

 
 

input FType_ FType = LPF; //滤波器类型

如此一来,在指标的对话框中选择该参数的值的情形如下图所示:

编辑切换为居中

添加图片注释,不超过 140 字(可选)

与枚举声明一样,命名常量后跟单行注释,然后它们被选作输入参数。现在,我们有了通用数字滤波器源代码的最终版本:

 
 

//+------------------------------------------------------------------+ //| ProjectName | //| Copyright 2010, CompanyName | //| http://www.companyname.net | //+------------------------------------------------------------------+ /* * <<< METATRADER 5 的数字滤波器 >>> * * * DF.dll 文件应放在 "\MetaTrader 5\MQL5\Libraries\" 文件夹下。 * DF.dll 需要另外三个DLLs,包括一个数学模块 * 处理 - bdsp.dll, lapack.dll, mkl_support.dll. * 对于Windows 32-位操作系统,这些 DLLs 必须安装到 "C:\Windows\System32\" 文件夹下 * 或者对于Windows 64-位操作系统,安装到 "C:\Windows\SysWOW64\" 文件夹下。 * * * 在使用前,请确保: * * 1. 终端设置中“允许加载DLL” 的选项已启用 * (Tools->Options->Expert Advisors tab). * 2. 在"C:\Windows\System32\" 或"C:\Windows\SysWOW64\" 文件夹下 * Bdsp.dll, lapack.dll and mkl_support.dll 辅助数学库存在。 * * 输入参数的描述: * * Ftype - 滤波器类型:0 - 低通滤波器 (FATL/SATL/KGLP), 1 - 高通滤波器 (KGHP), * 2 - 带通滤波器 (RBCI / KGBP), 3 - 带阻滤波器 (KGBS) * P1 - 截断周期1,以柱形个数计 * D1 - 稳态过程截断周期1,以柱形个数计 * A1 - 延时带1的衰减,单位dB * P2 - 截断周期2,以柱形个数计 * D2 - 稳态过程截断周期1,以柱形个数计 * A2 - 延时带2的衰减,单位dB * Ripple - 带宽, 单位dB * Delay - 延迟,以柱形计 * * 对于低通滤波器和HPF,P2, D2, A2 的值可忽略 * * 条件: * 低通滤波器: P1>D1 * 高通滤波器: P1<D1 * 带通滤波器和带阻滤波器:D2>P2>P1>D1 */

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值