Ti stai perdendo delle opportunità di trading:
- App di trading gratuite
- Oltre 8.000 segnali per il copy trading
- Notizie economiche per esplorare i mercati finanziari
Registrazione
Accedi
Accetti la politica del sito e le condizioni d’uso
Se non hai un account, registrati
Ehi, indicatore interessante. Mi piace l'aspetto matematico dell'utilizzo di un modello di proiezione sui grafici. Non ho ancora molta esperienza con il codice, quindi mi chiedo come si possa impostare il modello in modo che "torni indietro" e faccia la curva di previsione che avrebbe dovuto fare un certo numero di tick fa (ad esempio, 100). In questo modo si potrebbe applicare a vari grafici e dare un'idea di quanto la realtà si discosti dal modello, magari utilizzandolo per identificare alcune caratteristiche di un mercato in cui il modello funziona bene, ecc.
Sì, uso Windows 7, darò un'occhiata
potresti voler eseguire mt5 in modalità portatile:
terminal.exe /portable
otterrete l'indicatore che lavora nella directory corrente di mt5 - utile per l'installazione di pendrive
per fargli fare il back-shift in tempo per testare la sua capacità di previsione:
alla riga 32 inserire:
input int TimeShift = 10; // quante barre si spostano indietro, utile per valutare la prevedibilità dell'indicatore
alla riga 54 sostituire:
PlotIndexSetInteger(0, PLOT_SHIFT, Nfut);
con:
PlotIndexSetInteger(0, PLOT_SHIFT, Nfut - TimeShift);
alla riga 55 inserire:
PlotIndexSetInteger(1, PLOT_SHIFT, -TimeShift);
alla riga 87 sostituire:
if(CopyRates(NULL, 0, 0, Npast, rates) <= 0) return(0);
con:
if(CopyRates(NULL, 0, TimeShift, Npast, rates) <= 0) return(0);
Vale la pena di dare un'occhiata.
Chi lo usa nel trading?
L'ho analizzato nella storia - è emerso che l'indicatore non tiene affatto conto del trend, ha previsto contro il trend per diverse migliaia di punti a cinque cifre, a mio parere dovrebbe essere utilizzato con un indicatore come MA/CCI/Bande di Bollinger, dove l'estrapolatore confermerà il segnale, altrimenti può rivelarsi un salasso.
Dovrebbe essere utilizzato al meglio sui timeframe più alti, su D1 ha previsto con incredibile precisione per un mese, ma quando è iniziato il trend, sono rimasto molto deluso (vedi ultimo paragrafo).
Grazie
Vale la pena di dare un'occhiata.
Chi lo usa nel commercio?
Sono anche molto curioso, se qualcuno usa gli estrapolatori nella propria TS, come esattamente? E quanto è promettente questa direzione di ricerca del Graal?
A livello puramente intuitivo sembra che questo sia ciò che serve, ma in qualche modo i test e le previsioni di questo estrapolatore si correlano molto male con la realtà, almeno per me è risultato così...
Potreste dirmi, per favore, qual è la scelta degli estrapolatori e quale di essi è il più accurato? Voglio dire che probabilmente non solo le serie di Fourier possono essere scomposte, i modi sono infiniti. Per esempio, si può partire dai modi più semplici e partire dall'incrocio della MA o del MACD e quindi prevedere la curva, e se non si è pigri, poi diverse scomposizioni empiriche, poi la media e poi ancora la copponazione.... In teoria posso immaginare come farlo, ma se inizio a cercare di codificarlo, non sarò in grado di farlo in un anno((((
Sarebbe bello se l'estrapolatore impostasse la distribuzione di probabilità per il futuro prossimo invece di tracciare una linea.
Sarebbe bello se l'estrapolatore impostasse la distribuzione di probabilità per il futuro prossimo, invece di tracciare una linea.
Penso che potrebbe essere così, se si fa pratica con photoshop))))
Indicatore interessante! Grazie al suo creatore.
Per verificare la qualità della sua previsione, ho aggiunto un ulteriore parametro Start al codice: da quale barra iniziare invece della barra zero.
Ho anche aggiunto un gestore di eventi per il movimento del mouse.
Per avviarlo è sufficiente premere Ctrl e muovere il mouse (consiglio di abilitare il mirino): la sua posizione sul grafico sarà Start.
È molto divertente osservarlo in dinamica.
Per spegnerlo, basta premere un tasto qualsiasi, tranne Ctrl.
//+--------------------------------------------------------------------------------------+
//| Fourier_Extrapolator_of_Price.mq5 |
//| Copyright 2010, gpwr |
//+--------------------------------------------------------------------------------------+
// aggiunta la possibilità di spostare lo Start ( premere CTRL)
#property copyright "gpwr"
#property version "1.00"
#property description "Extrapolation of open prices by trigonometric (multitone) model"
#property indicator_chart_window
#property indicator_buffers 2
#property indicator_plots 2
//--- output del modello futuro
#property indicator_label1 "Modeled future"
#property indicator_type1 DRAW_LINE
#property indicator_color1 Red
#property indicator_style1 STYLE_SOLID
#property indicator_width1 1
//--- output del modello passato
#property indicator_label2 "Modeled past"
#property indicator_type2 DRAW_LINE
#property indicator_color2 Blue
#property indicator_style2 STYLE_SOLID
#property indicator_width2 1
//--- costanti globali
#define pi 3.141592653589793238462643383279502884197169399375105820974944592
//--- input dell'indicatore
input int Npast =300; // Barre passate, alle quali viene applicata la serie trigonometrica
input int Nfut =50; // Barre future previste
input int Nharm =20; // Narmoniche nel modello
input double FreqTOL =0.00001; // Tolleranza dei calcoli di frequenza
input int Start =0; // Da quale barra partiamo
//--- variabili globali
int N;
int key=0;
int start=0;
//--- buffer degli indicatori
double ym[],xm[];
//+------------------------------------------------------------------+
//| Funzione di inizializzazione dell'indicatore personalizzata |
//+------------------------------------------------------------------+
void OnInit()
{
//--- inizializzare le variabili globali
N=MathMax(Npast,Nfut+1);
//--- mappatura dei buffer degli indicatori
ArraySetAsSeries(xm,true);
ArraySetAsSeries(ym,true);
SetIndexBuffer(0,ym,INDICATOR_DATA);
SetIndexBuffer(1,xm,INDICATOR_DATA);
IndicatorSetInteger(INDICATOR_DIGITS,_Digits);
IndicatorSetString(INDICATOR_SHORTNAME, "Fourier("+string(Npast)+")");
PlotIndexSetInteger(0,PLOT_SHIFT,Nfut);
ChartSetInteger(0,CHART_EVENT_MOUSE_MOVE,true);
start=Start;
}
//+------------------------------------------------------------------+
//| Funzione di iterazione dell'indicatore personalizzato |
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
const int prev_calculated,
const datetime& Time[],
const double& Open[],
const double& High[],
const double& Low[],
const double& Close[],
const long& tick_volume[],
const long& volume[],
const int& spread[])
{
{ // Verifica dati insufficienti
if(rates_total<Npast)
{
Print("Errore: non ci sono abbastanza barre nella storia!");
return(0);
}
//--- inizializzare i buffer degli indicatori a EMPTY_VALUE
ArrayInitialize(xm,EMPTY_VALUE);
ArrayInitialize(ym,EMPTY_VALUE);
//--- rendere disponibili tutti i prezzi
MqlRates rates[];
ArraySetAsSeries(rates,true);
if(CopyRates(NULL,0,start,Npast,rates)<=0) return(0);
//--- ciclo principale
//--- preparare i dati di input
double x[];
ArrayResize(x,Npast);
double av=0;
for(int i=0;i<Npast;i++)
{
x[i]=rates[i].open;
av+=x[i];
}
av/=Npast;
//--- inizializzare le uscite del modello
for(int i=0;i<N<N;i++)
{
{ xm[i+start]=av;
if(i<=Nfut) ym[i+start]=av;
}
//--- adattare il modello trigonometrico e calcolare le previsioni
for(int harm=1;harm<=Nharm;harm++)
{
double w,m,a,b;
Freq(x,Npast,w,m,a,b);
for(int i=0;i<N;i++)
{
xm[i+start]+=m+a*MathCos(w*i)+b*MathSin(w*i);
if(i<=Nfut) ym[Nfut-i+start]+=m+a*MathCos(w*i)-b*MathSin(w*i);
}
}
return(rates_total);
}
//--- gestore di eventi per la pressione di Ctrl e il movimento del mouse
void OnChartEvent(const int id, // identificatore dell'evento
const long& lparam, // parametro dell'evento di tipo long
const double& dparam, // parametro dell'evento di tipo double
const string& sparam // parametro dell'evento di tipo string
)
{
double y;
int window=0;
datetime ttt;
if(id==CHARTEVENT_KEYDOWN) key=(int)lparam;
if(id==CHARTEVENT_MOUSE_MOVE && key==17)
{
ChartXYToTimePrice(0,(int)lparam,(int)dparam,window,ttt,y);
if(ttt!=0) start=iBarShift(NULL,0,ttt,false);
Comment("x = ",lparam,", y = ",dparam,", Price = ",y,", start = ",start);
ArrayInitialize(xm,EMPTY_VALUE);
ArrayInitialize(ym,EMPTY_VALUE);
//--- rendere disponibili tutti i prezzi
MqlRates rates[];
ArraySetAsSeries(rates,true);
if(CopyRates(NULL,0,start,Npast,rates)<=0) return;
//--- ciclo principale
//--- preparare i dati di input
double x[];
ArrayResize(x,Npast);
double av=0;
for(int i=0;i<Npast;i++)
{
x[i]=rates[i].open;
av+=x[i];
}
av/=Npast;
//--- inizializzare le uscite del modello
for(int i=0;i<N;i++)
{
xm[i+start]=av;
if(i<=Nfut) ym[i+start]=av;
}
//--- adattare il modello trigonometrico e calcolare le previsioni
for(int harm=1;harm<=Nharm;harm++)
{
double w,m,a,b;
Freq(x,Npast,w,m,a,b);
for(int i=0;i<N;i++)
{
xm[i+start]+=m+a*MathCos(w*i)+b*MathSin(w*i);
if(i<=Nfut) ym[Nfut-i+start]+=m+a*MathCos(w*i)-b*MathSin(w*i);
}
}
}
}
//+------------------------------------------------------------------+
//| Algoritmo di Quinn e Fernandes per trovare la frequenza |
//+------------------------------------------------------------------+
void Freq(double& x[],int n,double& w,double& m,double& a,double& b)
{
double z[];
ArrayResize(z,n);
double alpha=0.0;
double beta=2.0;
z[0]=x[0]-xm[0+start];
while(MathAbs(alpha-beta)>FreqTOL)
{
alpha=beta;
z[1]=x[1]-xm[1+start]+alpha*z[0];
double num=z[0]*z[1];
double den=z[0]*z[0];
for(int i=2;i<n;i++)
{
z[i]=x[i]-xm[i+start]+alpha*z[i-1]-z[i-2];
num+=z[i-1]*(z[i]+z[i-2]);
den+=z[i-1]*z[i-1];
}
beta=num/den;
}
w=MathArccos(beta/2.0);
TrigFit(x,n,w,m,a,b);
}
//+------------------------------------------------------------------+
//|Adattamento ai minimi quadrati di serie trigonometriche |
//+------------------------------------------------------------------+
void TrigFit(double& x[],int n,double w,double& m,double& a,double& b)
{
double Sc =0.0;
double Ss=0.0;
double Scc=0.0;
double Sss=0.0;
double Scs=0.0;
double Sx=0.0;
double Sxc=0.0;
double Sxs=0.0;
for(int i=0;i<n;i++)
{
double c=MathCos(w*i);
double s=MathSin(w*i);
double dx=x[i]-xm[i+start];
Sc +=c;
Ss +=s;
Scc+=c*c;
Sss+=s*s;
Scs+=c*s;
Sx +=dx;
Sxc+=dx*c;
Sxs+=dx*s;
}
Sc /=n;
Ss /=n;
Scc/=n;
Sss/=n;
Scs/=n;
Sx /=n;
Sxc/=n;
Sxs/=n;
if(w==0.0)
{
m=Sx;
a=0.0;
b=0.0;
}
else
{
// calcolo di a, b e m
double den=MathPow(Scs-Sc*Ss,2)-(Scc-Sc*Sc)*(Sss-Ss*Ss);
a=((Sxs-Sx*Ss)*(Scs-Sc*Ss)-(Sxc-Sx*Sc)*(Sss-Ss*S))/den;
b=((Sxc-Sx*Sc)*(Scs-Sc*Sc*Ss)-(Sxs-Sx*Ss)*(Scc-Sc*Sc*Sc))/den;
m=Sx-a*Sc-b*Ss;
}
}
int iBarShift(string symbol,int timeframe,datetime time,bool exact=false)
{
if(time<0) return(-1);
ENUM_TIMEFRAMES tf=TFMigrate(timeframe);
datetime Arr[],time1;
CopyTime(simbolo,tf,0,1,Arr);
time1=Arr[0];
if(CopyTime(symbol,tf,time,time1,Arr)>0)
{
if(ArraySize(Arr)>2) return(ArraySize(Arr)-1);
if(time<time1) return(1);
else return(0);
}
else return(-1);
}
ENUM_TIMEFRAMES TFMigrate(int tf)
{
switch(tf)
{
case 0: return(PERIOD_CURRENT);
case 1: return(PERIOD_M1);
case 5: return(PERIOD_M5);
case 15: return(PERIOD_M15);
case 30: return(PERIOD_M30);
case 60: return(PERIOD_H1);
case 240: return(PERIOD_H4);
case 1440: return(PERIOD_D1);
case 10080: return(PERIOD_W1);
case 43200: return(PERIOD_MN1);
case 2: return(PERIOD_M2);
case 3: return(PERIOD_M3);
case 4: return(PERIOD_M4);
case 6: return(PERIOD_M6);
case 10: return(PERIOD_M10);
case 12: return(PERIOD_M12);
case 16385: return(PERIOD_H1);
case 16386: return(PERIOD_H2);
case 16387: return(PERIOD_H3);
case 16388: return(PERIOD_H4);
case 16390: return(PERIOD_H6);
case 16392: return(PERIOD_H8);
case 16396: return(PERIOD_H12);
case 16408: return(PERIOD_D1);
case 32769: return(PERIOD_W1);
case 49153: return(PERIOD_MN1);
default: return(PERIOD_CURRENT);
}
}
...