128 lignes
4,4 Kio
MQL5
128 lignes
4,4 Kio
MQL5
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| BOSSNoiseSweep.mq5|
|
||
|
|
//| MMQ — Muhammad Minhas Qamar |
|
||
|
|
//| www.mql5.com/en/articles/23491 |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
#property copyright "MMQ — Muhammad Minhas Qamar"
|
||
|
|
#property link "https://www.mql5.com/en/articles/23491"
|
||
|
|
#property description "Sweeps the retained-coefficient count against a rising noise level on a trend-vs-range task and prints an accuracy grid."
|
||
|
|
#property version "1.00"
|
||
|
|
#property strict
|
||
|
|
|
||
|
|
#include <BOSS\BOSS.mqh>
|
||
|
|
|
||
|
|
input int Alphabet = 4;
|
||
|
|
input int Window = 24;
|
||
|
|
input int SeriesLen = 240;
|
||
|
|
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| Trending shape: drift plus a small oscillation and noise. |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
void MakeTrend(double &out[],int len,double noise)
|
||
|
|
{
|
||
|
|
ArrayResize(out,len);
|
||
|
|
for(int i=0;i<len;i++)
|
||
|
|
out[i]=0.02*i+0.5*MathSin(2.0*M_PI*i/Window)+noise*(MathRand()/32767.0-0.5);
|
||
|
|
}
|
||
|
|
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| Ranging shape: clean oscillation about a flat mean plus noise. |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
void MakeRange(double &out[],int len,double noise)
|
||
|
|
{
|
||
|
|
ArrayResize(out,len);
|
||
|
|
for(int i=0;i<len;i++)
|
||
|
|
out[i]=MathSin(2.0*M_PI*i/Window)+noise*(MathRand()/32767.0-0.5);
|
||
|
|
}
|
||
|
|
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| Build a broad window pool (both shapes) for MCB fitting. |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
void BuildWindows(double &windows[],int &count,int win,double noise)
|
||
|
|
{
|
||
|
|
int per=150;
|
||
|
|
count=per*2;
|
||
|
|
ArrayResize(windows,count*win);
|
||
|
|
double s[];
|
||
|
|
int idx=0;
|
||
|
|
for(int r=0;r<per;r++)
|
||
|
|
{
|
||
|
|
MakeTrend(s,win,noise);
|
||
|
|
for(int i=0;i<win;i++)
|
||
|
|
windows[idx*win+i]=s[i];
|
||
|
|
idx++;
|
||
|
|
MakeRange(s,win,noise);
|
||
|
|
for(int i=0;i<win;i++)
|
||
|
|
windows[idx*win+i]=s[i];
|
||
|
|
idx++;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| Accuracy of a trend/range classifier at a given query noise. |
|
||
|
|
//| Trains one clean prototype per class, then classifies fresh |
|
||
|
|
//| noisy series of both shapes and returns overall accuracy. |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
double AccuracyAt(int word_len,double train_noise,double query_noise)
|
||
|
|
{
|
||
|
|
double windows[];
|
||
|
|
int nwin;
|
||
|
|
BuildWindows(windows,nwin,Window,train_noise);
|
||
|
|
|
||
|
|
CBossClassifier clf;
|
||
|
|
if(!clf.Build(word_len,Alphabet,windows,nwin,Window))
|
||
|
|
return -1.0;
|
||
|
|
|
||
|
|
double s[];
|
||
|
|
MakeTrend(s,SeriesLen,train_noise);
|
||
|
|
clf.AddExample(s,SeriesLen,"trend");
|
||
|
|
MakeRange(s,SeriesLen,train_noise);
|
||
|
|
clf.AddExample(s,SeriesLen,"range");
|
||
|
|
|
||
|
|
int correct=0, trials=40, total=0;
|
||
|
|
double bd;
|
||
|
|
for(int t=0;t<trials;t++)
|
||
|
|
{
|
||
|
|
MakeTrend(s,SeriesLen,query_noise);
|
||
|
|
if(clf.Classify(s,SeriesLen,bd)=="trend")
|
||
|
|
correct++;
|
||
|
|
total++;
|
||
|
|
MakeRange(s,SeriesLen,query_noise);
|
||
|
|
if(clf.Classify(s,SeriesLen,bd)=="range")
|
||
|
|
correct++;
|
||
|
|
total++;
|
||
|
|
}
|
||
|
|
return 100.0*correct/total;
|
||
|
|
}
|
||
|
|
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
//| Print the WordLen x noise accuracy grid. |
|
||
|
|
//+------------------------------------------------------------------+
|
||
|
|
void OnStart()
|
||
|
|
{
|
||
|
|
MathSrand(20260712);
|
||
|
|
|
||
|
|
int wls[3] = {2,3,4};
|
||
|
|
double noises[5]= {0.1,0.3,0.5,1.0,1.5};
|
||
|
|
|
||
|
|
//--- header row
|
||
|
|
string hdr=" WordLen |";
|
||
|
|
for(int n=0;n<5;n++)
|
||
|
|
hdr+=StringFormat(" noise=%.1f",noises[n]);
|
||
|
|
Print("=== BOSS accuracy: retained coefficients vs query noise ===");
|
||
|
|
Print(" (trained at low noise 0.07; trend-vs-range; chance = 50%)");
|
||
|
|
Print(hdr);
|
||
|
|
|
||
|
|
for(int w=0;w<3;w++)
|
||
|
|
{
|
||
|
|
string row=StringFormat(" %2d (%dL) |",wls[w],wls[w]*2);
|
||
|
|
for(int n=0;n<5;n++)
|
||
|
|
{
|
||
|
|
double acc=AccuracyAt(wls[w],0.07,noises[n]);
|
||
|
|
row+=StringFormat(" %5.0f%%",acc);
|
||
|
|
}
|
||
|
|
Print(row);
|
||
|
|
}
|
||
|
|
Print("=== sweep complete ===");
|
||
|
|
}
|
||
|
|
//+------------------------------------------------------------------+
|