//+------------------------------------------------------------------+ //| iK_tay_v01.mq4 | //| Ivan Katsko | //+------------------------------------------------------------------+ #property copyright "Ivan Katsko" #property link "" #property indicator_separate_window // Отображение в отдельном окне #property indicator_buffers 7 // Количество буферов #property indicator_color1 DeepPink // Цвет первой линии #property indicator_color2 Purple // Цвет второй линии #property indicator_color3 Red // Цвет третьей линии #property indicator_color4 LawnGreen // Цвет червертой линии #property indicator_color5 Gold // Цвет пятой линии #property indicator_color6 DarkBlue // Цвет шестой линии #property indicator_color7 SteelBlue // Цвет седьмой линии extern int Discret=1; // Дискретность подбора: 1 - каждая позиция; 2 - через позицию и т.д. extern double Level=10; // Минимальный уровень SL/TP int i,j,x, Repeat_Count=30, // Количество повторов Action_Count, // Количество сделок History, // Колич.баров в расчётной истории Iteration; // Колич.итераций static datetime New_Time; double k, // Коэф. Alg_Minus=-0.001, // Алгоритм: "сегодня - не как вчера" Alg_Plus = 0.001, // Алгоритм: "сегодня - как вчера" Buy = 0.001, // Величина индикатора Sell=-0.001, // Величина индикатора Scope_Up, // Размах Вверх Scope_Dn, // Размах Вниз Max_Alg_Minus, // Максимум для алгоритма "минус" Max_Alg_Plus, // Максимум для алгоритма "плюс" Max_Value=-0.1, YT_Alg_Minus, TP_Alg_Minus, SL_Alg_Minus, Set_Alg_Minus, YT_Alg_Plus, TP_Alg_Plus, SL_Alg_Plus, Set_Alg_Plus, Scope_Cl, // Размах закрытия Repeat[30,3], // Массив повторов повторить Algoritm[], // Алгоритм: 1 - "сегодня как вчера", -1 - "сегодня не как вчера" Direction[], // Направление приказа: 1 - покупка, -1 - продажа Value_TP[], // Массив - Значение Тейк Профит далее будет переопределен размер Sum_TP[], // Массив - Нарастающей адаптивной суммы Тейк Профит Sum_na_TP[], // Массив - Нарастающей суммы Тейк Профит Im_Sum_TP[30], // Массив - промежуточной Нарастающей суммы Тейк Профит Spread, // Спред Set_YT, // Заданный размах "вчера" Set_TP[], // Заданный Тейк Профит Set_SL[], // Заданный Стоп Лосс Found_TP, // Найденное значение Тейк Профит Found_SL, // Найденное значение Стоп Лосс Found_Scope_YT; // Найденный размах "вчера" bool New_Bar=false; // Флаг нового бара //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ int init() { if (Discret<=0) { Discret=1; // Не корректно введен дискрет Alert ("Дискретность установлена равной 1"); } New_Time=Time[0]; // Время текущего бара Spread=MarketInfo(Symbol(), MODE_SPREAD)*Point; SetIndexBuffer(0,Set_TP); // Назначение массива Тейк Профит SetIndexStyle (0,DRAW_LINE,STYLE_SOLID,2); // Стиль линии SetIndexBuffer(1,Set_SL); // Назначение массива Стоп Лосс SetIndexStyle (1,DRAW_LINE,STYLE_SOLID,1); // Стиль линии SetIndexBuffer(2,Sum_TP); // Назначение массива сумма профита SetIndexStyle (2,DRAW_LINE,STYLE_SOLID,2); // Стиль линии SetIndexBuffer(3,Direction); // Назначение массива Направление торговли SetIndexStyle (3,DRAW_HISTOGRAM,STYLE_SOLID,4); // Стиль линии SetIndexBuffer(4,Algoritm); // Назначение массива алгоритма SetIndexStyle (4,DRAW_LINE,STYLE_SOLID,1); // Стиль линии SetIndexBuffer(5,Value_TP); // Назначение массива Профита SetIndexStyle (5,DRAW_HISTOGRAM,STYLE_SOLID,2); // Стиль линии switch (Period()) // Установка колич.исследуемых баров { case 5: History = 24; break; // Период 5-ти минутный case 15: History = 24; break; // Период 15-ти минутный case 30: History = 24; break; // Период 30-ти минутный case 60: History = 24; break; // Период часовой case 240: History = 30; break; // Период 4-х часовой case 1440: History = 22; break; // Период дневной default: Alert("Выберите период от M5 до D1."); break;// Неверно выбран период } return(0); } //+------------------------------------------------------------------+ int start() { Fun_New_Bar(); // Определение начала нового бара for (int n=1; n<3; n++) // Для двух вариантов алгоритмов { Fun_Sum_TP(10*Point,10*Point,10*Point,Alg_Minus); // Ищем число итераций (равно наибольшему размаху) Set_YT =0.5*Iteration*Discret*Point; // Начальный размах "вчера" Set_SL[0]=0.5*Iteration*Discret*Point; // Начальный Стоп Лосс Set_TP[0]=0.5*Iteration*Discret*Point; // Начальный Тейк Профит Alg_Minus=-0.25*Set_SL[0]; Alg_Plus = 0.25*Set_TP[0]; if (n==1) Algoritm[0]=Alg_Minus; // Первый проход - алгоритм "сегодня не как вчера" if (n==2) Algoritm[0]=Alg_Plus; // Второй проход - алгоритм "сегодня как вчера" Repeat_Count=5+History/MathSqrt(Iteration*Discret/10); ArrayResize(Repeat,Repeat_Count); // Изменен размер массива ArrayResize(Im_Sum_TP,Repeat_Count); // Изменен размер массива ArrayInitialize(Im_Sum_TP,0); // Очистить массив сумм ArrayInitialize(Repeat,0); // Очистить массив повторов Action_Count=0; // Обнулим счетчик количества сделок x=0; // Сбросить индекс массив повторов while (Action_Count=Max_Alg_Plus) // Если лучшим оказался адгоритм "минус" { Max_Value=Max_Alg_Minus; Set_YT=YT_Alg_Minus; for (i=0; i0) Algoritm[i]=Set_Alg_Minus; else Algoritm[i]=0; Alg_Minus=Set_Alg_Minus; } } else { Max_Value=Max_Alg_Plus; Set_YT=YT_Alg_Plus; for (i=0; i0) Algoritm[i]=Set_Alg_Plus; else Algoritm[i]=0; Alg_Plus=Set_Alg_Plus; } } Buy = 0.5*Set_YT; Sell=-0.5*Set_SL[0]; Fun_Sum_TP(Set_YT,Set_SL[0],Set_TP[0],Algoritm[0]); // Нарисуем окончательный график return(0); } //+------------------------------------------------------------------+ double Fun_Sum_TP(double set_YT, // Ф-ия определения нарастающего значения Тейк Профит double set_SL,double set_TP,double algoritm) { int i, // Индекс бара Count_bars; // Количество просчитанных баров ArrayResize(Sum_na_TP,ArraySize(Sum_TP)); Sum_TP[History]=0; // Обнулим последние значения Sum_na_TP[History]=0; Direction[History]=0; Value_TP[History-1]=0; i=Bars-1; // Индекс первого if (i>History-1) // Если много баров то .. i=History-1; // ..рассчитывать заданное колич. while(i>=0) // Цикл по барам { //---- Определим размах Scope_Up=(High[i] -Open[i]); // Значение Размаха Вверх на i-ом баре Scope_Dn=(Low[i] -Open[i]); // Значение Размаха Вниз на i-ом баре Scope_Cl=(Close[i]-Open[i]); // Значение Размаха Закрытия на i-ом баре //---- Определим количество итераций if ( Scope_Up>Iteration*Discret*Point) Iteration= (Scope_Up/Point)/Discret; if (-Scope_Dn>Iteration*Discret*Point) Iteration=(-Scope_Dn/Point)/Discret; //---- Определим направление приказа if ((Scope_Up>=(-Scope_Dn) // Если размах вверх больше размаха вниз && Scope_Up>=set_YT // больше заданного размаха "вчера" && algoritm==Alg_Plus) // задан алгоритм "сегодня как вчера" || // ИЛИ (Scope_Up<(-Scope_Dn) // Если размах вниз больше размаха вверх && (-Scope_Dn)>=set_YT // больше заданного размаха "вчера" && algoritm==Alg_Minus)) // задан алгоритм "сегодня не как вчера" { Direction[i]=Buy; // надо покупать } if ((Scope_Up>(-Scope_Dn) // Если размах вверх больше размаха вниз && Scope_Up>=set_YT // больше заданного размаха "вчера" && algoritm==Alg_Minus) // задан алгоритм "сегодня не как вчера" || // ИЛИ (Scope_Up<(-Scope_Dn) // Если размах вниз больше размаха вверх && (-Scope_Dn)>=set_YT // больше заданного размаха "вчера" && algoritm==Alg_Plus)) // задан алгоритм "сегодня как вчера" { Direction[i]=Sell; // надо продавать } if ((Scope_Up>=(-Scope_Dn) // Если размах вверх больше размаха вниз && Scope_Up=(set_TP+Spread) // размах вверх больше Тейк Профита + Спред && (-Scope_Dn)<(set_SL-Spread)) // размах вниз меньше Стоп Лосса - Спред || // ИЛИ (Direction[i+1]==Sell // Если надо продавать && (-Scope_Dn)>=(set_TP+Spread) // размах вниз больше Тейк Профита + Спред && Scope_Up<(set_SL-Spread))) // размах вверх меньше Стоп Лосса - Спред Value_TP[i]=set_TP; // получен заданный Тейк Профит //---- Определим значения Тейк Профит при проигрыше if ((Direction[i+1]==Buy // Если надо покупать && (-Scope_Dn)>=(set_SL-Spread)) // размах вниз меньше Стоп Лосса - Спред || // ИЛИ (Direction[i+1]==Sell // Если надо продавать && Scope_Up>=(set_SL-Spread))) // размах вверх меньше Стоп Лосса - Спред Value_TP[i]=-set_SL; // получен заданный Тейк Профит //---- Определим значения Тейк Профит в других случаях if (Direction[i+1]==0) Value_TP[i]=0;// Если направление не определено - Тейк Профит равен нулю if ((Direction[i+1]==Buy // Если надо покупать && Scope_Up<(set_TP+Spread) // размах вверх меньше Тейк Профита + Спред && (-Scope_Dn)<(set_SL-Spread) // размах вниз меньше Стоп Лосса - Спред && Scope_Cl>=0) || // ИЛИ (Direction[i+1]==Sell // Если надо продавать && (-Scope_Dn)<(set_TP+Spread) // размах вниз меньше Тейк Профита + Спред && Scope_Up<(set_SL-Spread) // размах вверх меньше Стоп Лосса - Спред && -Scope_Cl>=0)) Value_TP[i]=MathAbs(Scope_Cl)-Spread; // Тейк Профит равен закрытию минус спред if ((Direction[i+1]==Buy // Если надо покупать && Scope_Up<(set_TP+Spread) // размах вверх меньше Тейк Профита + Спред && (-Scope_Dn)<(set_SL-Spread) // размах вниз меньше Стоп Лосса - Спред && Scope_Cl<0) || // ИЛИ (Direction[i+1]==Sell // Если надо продавать && (-Scope_Dn)<(set_TP+Spread) // размах вниз меньше Тейк Профита + Спред && Scope_Up<(set_SL-Spread) // размах вверх меньше Стоп Лосса - Спред && -Scope_Cl<0)) Value_TP[i]=-(MathAbs(Scope_Cl)+Spread); // Тейк Профит равен закрытию минус спред //---- Определим нарастающее значение Тейк Профит k=i; Sum_TP[i]=Sum_TP[i+1]+Value_TP[i]/((k+10)/10); Sum_na_TP[i]=Sum_na_TP[i+1]+Value_TP[i]; i--; // Расчёт индекса следующего бара } return(0); // возвращаемое значение } //+------------------------------------------------------------------+ void Fun_New_Bar() // Ф-ия обнаружения нового бара { New_Bar=false; // Нового бара нет if(New_Time!=Time[0]) // Сравниваем время { New_Time=Time[0]; // Теперь время такое New_Bar=true; // Поймался новый бар } } //+------------------------------------------------------------------+ bool Fun_Repeat(double yt,double sl,double tp ) // Ф-ия сравнения с массивом повторов { for (int X=0; X