Общие вопросы по разработке > Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Общие вопросы по разработке в Альфа-Директ 4. Обсуждение разработки пользовательских индикаторов, стратегий.
Владимир
Сообщения: 84
Зарегистрирован: 14 ноя 2016, 02:17
Благодарил (а): 3 раза
Поблагодарили: 5 раз

Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Непрочитанное сообщение Владимир » 28 май 2019, 00:07

Доброго времени суток!
Пробуем написать простенького робота который открыть позицию на последних 30 секундах формирования свечи!

Код: Выделить всё

function Initialize()
{
   StrategyName = "Paterny_v1";
   UseClosedBar=false; //разрешение на открывание позиции внутри бара

   LongLimit = 10;
   ShortLimit = -10;
   AddGlobalVariable("ON_OFF", Types.Boolean, false);
   AddGlobalVariable("path", Types.String, @"c:\\dell\\RobotSearch_level.txt");
   AddInput("Input1", Inputs.Candle, 5, true, "SRM9=ФОРТС");
   
}

function OnUpdate()
{
TimeSpan Delta = new TimeSpan(0, 04, 30);
TimeSpan Interval = BarTime()+Delta;
TimeSpan Time_0;
Time_0=DateTime.Now.TimeOfDay;

if (Time_0>=Interval)
{ON_OFF=true;}
else
{ON_OFF=false;}

using (System.IO.StreamWriter sw = System.IO.File.CreateText(path))
      {
         sw.WriteLine("время BarTime = "   + BarTime().ToString());
         sw.WriteLine("системное время =  "   + Time_0.ToString());
         sw.WriteLine("BarTime()+Delta + 4.30 =  "   + Interval.ToString());
         sw.WriteLine("ON_OFF =  "   + ON_OFF.ToString());
         sw.Close(); sw.Dispose();
      }
   
if(ON_OFF==true)   //Разрешаем открывать позицию за  30 секунд до закрытия свечи (примерно 30секунд)
   {
   /// ПРАВИЛО 1
   if (Input1.Open< Input1.Close )
   {
      EnterLong();
   //   StopLoss(0.1, SignalPriceType.DeltaInPercentFromAveragePrice);
   }
   /// ПРАВИЛО 2
   if (Input1.Open> Input1.Close )
   {
      EnterShort();
   //   StopLoss(0.1, SignalPriceType.DeltaInPercentFromAveragePrice);
   }



   }
}


Вложения
000.jpg

Владимир
Сообщения: 84
Зарегистрирован: 14 ноя 2016, 02:17
Благодарил (а): 3 раза
Поблагодарили: 5 раз

Re: Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Непрочитанное сообщение Владимир » 31 май 2019, 18:59

Роботом на последних секунда с использованием индикаторов возникают некоторые нюансы!
2019.05.31 17:34:06.139 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:34:11.178 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:34:16.763 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:34:22.176 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:34:27.230 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:34:32.316 Разрешаем открывать позицию за 30 секунд ON_OFF = True
2019.05.31 17:37:22.934 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:28.347 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:34.446 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:39.485 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:44.898 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:52.199 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:37:57.238 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:02.355 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:07.378 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:12.510 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:17.596 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:23.259 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:28.235 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:33.742 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:39.046 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:44.335 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:49.389 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:38:56.379 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:02.884 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:08.219 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:13.352 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:18.375 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:23.585 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:29.700 Разрешаем открывать позицию за 30 секунд ON_OFF = False
2019.05.31 17:39:37.984 Разрешаем открывать позицию за 30 секунд ON_OFF = True

По логу видно, что робот запускает функцию function OnUpdate() примерно каждые 5 секунд

Дальше происходит следующее если робот управляет построением линии индикатора

1.jpg

2.jpg
2.jpg (104.85 КБ) 18490 просмотров

То есть если индикатор рисует линию по запросу как в этом индикаторе (код упростил до минимума)

Код: Выделить всё

function Initialize()
{
// Обязательные параметры:
    IndicatorName = "Search_level_Robot";   // Задайте название индикатора и сохраните с данным именем
   PriceStudy = true;   // Рисовать в области цены (true – да, false – нет)
   AddInput("Input", Inputs.Candle);   // Input - входной ряд (Inputs.Price) или свечи (Inputs.Candle)

   AddSeries("Last1", DrawAs.Line, Color.Red);// Задаем вид линии индикатора с именем ряда Last
   AddLevel(0, Color.Red, LineStyles.Dot, 2, "Last");
   
    //Данные получаемые с робота
    AddParameter("GetPriceStep_ind", 0);      // Минимальный шаг цены получаемый с робота (число знаков после запятой)
   AddParameter("Period", 200);            // Период построения уровней
    AddParameter("Enable_Recalculation", 1);   // Разрешение на обработку данных
    AddParameter("max_stop", 20);            // Период построения уровней (длинна истории)
    AddParameter("gap", 4);                  // Период построения уровней (длинна истории)

    //Данные передаваемые в робот
   AddSeries("Direction");                  // Направление открываемой позиции (0 - нет направления, 1- лонг, 2- шорт)
   
   AddGlobalVariable("ListDouble", Types.DoubleList);
   AddGlobalVariable("path", Types.String, @"c:\\dell\\Search_level_Robot.txt");
}
function Evaluate()
{
 /*
 код индикатора
 */
    if (Direction>0 && (Convert.ToBoolean(Enable_Recalculation)==true))
   {   //Открываем позицию вконце формирования свечи с индексом[0] (за 30 секунд до закрытия свечи)
   Levels[0].Level = ListDouble[0];
   }
   
}


Код: Выделить всё

/**
Тестируем патерны по А.М. Грчика, описанные в индикаторе Search_level.
Пытаемся открыть позицию на последних 30 секундах формирования свечи
( UseClosedBar = false;)
Algorithm = Отбой от уровня;
**/

function Initialize()
{
   StrategyName = "Paterny_v1";
   UseClosedBar=false; //разрешение на открывание позиции внутри бара
    AddParameter("GetPriceStep_ind", 0, "Минимальный шаг цены (число знаков после запятой)" , 1);      // Минимальный шаг цены получаемый с робота (число знаков после запятой)
   AddParameter("Period", 200, "Период построения уровней",1);                  // Период построения уровней
   AddParameter("Enable_Recalculation", 1, "Разрешение на пересчёт индикатора", 1);
   AddParameter("max_stop", 20, "Максимальный стоп", 1);
   AddParameter("gap", 4, "Величина проскальзования", 1);
   AddParameter("Direction", 0, "Направление открываемой позиции", 1);   // Направление открываемой позиции (0 - нет направления, 1- лонг, 2- шорт)

   AddInput("Input1", Inputs.Candle, 5, true, "SRM9=ФОРТС");
   LongLimit = 1;
   ShortLimit = -1;
   AddGlobalVariable("ON_OFF", Types.Boolean, false);               //Разрешаем открывать позицию за  30 секунд до закрытия свечи (примерно 30секунд)
   AddGlobalVariable("ON_OFF_Recalculation", Types.Boolean, true);   //Расчёт исходных значений инструмента
   
   AddGlobalVariable("path", Types.String, @"c:\\dell\\RobotSearch_level.txt");
AddChartIndicator("MY.Search_level_Robot", new Dictionary <string, string>{{"GetPriceStep_ind", "GetPriceStep_ind"},{"Period", "Period"},{"Enable_Recalculation", "Enable_Recalculation"},{"max_stop", "max_stop"},{"gap", "gap"}});

}

function OnUpdate()
{
//Расчёт исходных значений инструмента (Однократный)
if (ON_OFF_Recalculation==true)   
    { //Рассчитываем колличество знаков после запятой в шаге цены
    int GetPriceStep_ind=0;
    while (GetPriceStep() * Math.Pow(10, 1 + GetPriceStep_ind) % 10 != 0) { GetPriceStep_ind++; }   
   
    //Рассчитываем величину стопа и проскальзывания
   max_stop=Math.Round((Input.High[0]*0.2/100),(GetPriceStep_ind));
   gap=Math.Round((max_stop*0.2),(GetPriceStep_ind));
   ON_OFF_Recalculation=false;
   }

TimeSpan Delta = new TimeSpan(0, 04, 30);
TimeSpan Interval = BarTime()+Delta;
TimeSpan Time_0;
Time_0=DateTime.Now.TimeOfDay;
if (Time_0>=Interval)
{
ON_OFF=true;
Enable_Recalculation=1;
LogData ("Разрешаем открывать позицию за  30 секунд ON_OFF = "  + Convert.ToString(ON_OFF),Name);
}
else
{
ON_OFF=false;
Enable_Recalculation=0;
LogData ("Разрешаем открывать позицию за  30 секунд ON_OFF = "  + Convert.ToString(ON_OFF),Name);
}

using (System.IO.StreamWriter sw = System.IO.File.CreateText(path))
      {
         sw.WriteLine("Расчёт исходных значений инструмента (Однократный)" );
         sw.WriteLine("Шаг цены = "   + Convert.ToString(GetPriceStep()));
         sw.WriteLine("Колличество знаков после запятой = "   + Convert.ToString(GetPriceStep_ind));
         sw.WriteLine("Величина стопа = "   + Convert.ToString(max_stop));
         sw.WriteLine("Величина проскальзования = "   + Convert.ToString(gap));
         sw.WriteLine("время BarTime = "   + BarTime().ToString());
         sw.WriteLine("системное время =  "   + Time_0.ToString());
         sw.WriteLine("BarTime()+Delta + 4.30 =  "   + Interval.ToString());
         sw.WriteLine("ON_OFF =  "   + ON_OFF.ToString());
         sw.Close(); sw.Dispose();
      }
      
   
if(ON_OFF==true)   //Разрешаем открывать позицию за  30 секунд до закрытия свечи (примерно 30секунд)
   {
   double price=(MY.Search_level_Robot(Input1, GetPriceStep_ind, Period, Enable_Recalculation, max_stop, gap).GetValue("Last1", 0));
LogData ("Разрешаем открывать позицию за  30 секунд - "  + Convert.ToString(MY.Search_level_Robot(Input1, 2, Period).GetValue("Dictionary")),Name);
LogData ("Цена уровня = "  + Convert.ToString(price),Name);
      
   /// ПРАВИЛО 1
      if (MY.Search_level_Robot(Input1, GetPriceStep_ind, Period, Enable_Recalculation, max_stop, gap).GetValue("Direction", 0) ==1)
      {
         EnterLongLimit(price+gap,1);
         BreakingStop(max_stop, (max_stop*4), SignalPriceType.Price);
      LogData ("заявка в лонг + стоп "  ,Name);
         
         //BreakingStop(0.1, 0.4, SignalPriceType.DeltaInPercentFromAveragePrice);      
      }
   
   /// ПРАВИЛО 2
      if (MY.Search_level_Robot(Input1, GetPriceStep_ind, Period, Enable_Recalculation, max_stop, gap).GetValue("Direction", 0) ==2)
      {
         EnterShortLimit(price-gap);
         BreakingStop(max_stop, (max_stop*4), SignalPriceType.Price);
         //BreakingStop(0.1, 0.4, SignalPriceType.DeltaInPercentFromAveragePrice);
         LogData ("заявка в шорт + стоп "  ,Name);

      }
   }
}




Робот выключается так как неможет обратиться к коду

Код: Выделить всё

double price=(MY.Search_level_Robot(Input1, GetPriceStep_ind, Period, Enable_Recalculation, max_stop, gap).GetValue("Last1", 0));
LogData ("Разрешаем открывать позицию за  30 секунд - "  + Convert.ToString(MY.Search_level_Robot(Input1, 2, Period).GetValue("Dictionary")),Name);

Лог приведён выше.
Значит надо контролировать время разрешение на построение линии индикатором, а нетолько открытия позиции роботом.
Хотелось бы, что бы "oxi" более детально рассказал про взаимодействие робота и индикатора (на каком такте (цикле) робот получает данные с индикатора и отправляет данные. Интерисует динамика (данные в переменной робота поменялись), как поведет себя индикатор. Когда вернутся новые данные?
Так же в роботе переменные меняешь, запускаешь робота когда они обновятся. (Пробоваль менять переменные менялись как то медленно).

Владимир
Сообщения: 84
Зарегистрирован: 14 ноя 2016, 02:17
Благодарил (а): 3 раза
Поблагодарили: 5 раз

Re: Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Непрочитанное сообщение Владимир » 31 май 2019, 21:36

Судя по логу создать правильно выполняемого кода не получится
время BarTime = 21:15:00
системное время = 21:18:21.9497438 время на компьютере
BarTime()+Delta1 + 3.00 = 21:18:00
Enable_Recalculation = True - разрешили пересчёт индикатора
BarTime()+Delta2 + 4.30 = 21:19:30
ON_OFF = False


и лог
2019.05.31 21:15:08.431 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:08.431 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:15:17.307 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:17.307 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:15:23.189 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:23.189 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:15:31.472 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:31.472 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:15:51.081 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:51.081 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:15:57.774 Разрешение индикатору за 45 секунд = false
2019.05.31 21:15:57.774 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:16:04.435 Разрешение индикатору за 45 секунд = false
2019.05.31 21:16:04.435 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:16:16.541 Разрешение индикатору за 45 секунд = false
2019.05.31 21:16:16.541 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:16:37.819 Разрешение индикатору за 45 секунд = false
2019.05.31 21:16:37.819 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:16:47.741 Разрешение индикатору за 45 секунд = false
2019.05.31 21:16:47.741 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:17:01.157 Разрешение индикатору за 45 секунд = false
2019.05.31 21:17:01.157 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:17:31.811 Разрешение индикатору за 45 секунд = false
2019.05.31 21:17:31.811 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:17:37.427 Разрешение индикатору за 45 секунд = false
2019.05.31 21:17:37.427 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:18:01.092 Разрешение индикатору за 45 секунд = true
2019.05.31 21:18:01.092 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:18:21.949 Разрешение индикатору за 45 секунд = true
2019.05.31 21:18:21.949 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:19:22.212 Разрешение индикатору за 45 секунд = true
2019.05.31 21:19:22.212 Разрешаем открывать позицию за 30 секунд = False
2019.05.31 21:19:52.039 Разрешение индикатору за 45 секунд = true
2019.05.31 21:19:52.039 Разрешаем открывать позицию за 30 секунд = True

стабильности временных интервалов нет
1 21:15:00 - 21:15:08 = 8 сек
2 21:15:17 - 21:15:08 = 9 сек
.......
х 21:16:16 - 21:16:04 = 12 сек
Судя по логам:
Робот в одном цикле отправляет данные в индикатор
В другом цикле индикатор производит расчёт и отправляет данные обратно
Ну а в третьем цикле происходит обработка данных в роботе!

Владимир
Сообщения: 84
Зарегистрирован: 14 ноя 2016, 02:17
Благодарил (а): 3 раза
Поблагодарили: 5 раз

Re: Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Непрочитанное сообщение Владимир » 01 июн 2019, 08:17

forts-12-1.png
forts-12-1.png (174.24 КБ) 18454 просмотра

Индикатор который должен был получать сигнал с робота на отрисовку линии при формировании потерна.

Код: Выделить всё

function Initialize()
{
// Обязательные параметры:
    IndicatorName = "Search_level_Robot";   // Задайте название индикатора и сохраните с данным именем
   PriceStudy = true;   // Рисовать в области цены (true – да, false – нет)
   AddInput("Input", Inputs.Candle);   // Input - входной ряд (Inputs.Price) или свечи (Inputs.Candle)

   AddSeries("Last1", DrawAs.Line, Color.Red);// Задаем вид линии индикатора с именем ряда Last
   AddLevel(0, Color.Red, LineStyles.Dot, 2, "Last");
   
    //Данные получаемые с робота
    AddParameter("GetPriceStep_ind", 0);      // Минимальный шаг цены получаемый с робота (число знаков после запятой)
   AddParameter("Period", 200);            // Период построения уровней
    AddParameter("Enable_Recalculation", 1);   // Разрешение на обработку данных
    AddParameter("max_stop", 20);            // Период построения уровней (длинна истории)
    AddParameter("gap", 4);                  // Период построения уровней (длинна истории)

    //Данные передаваемые в робот
   AddSeries("Direction");                  // Направление открываемой позиции (0 - нет направления, 1- лонг, 2- шорт)
   
   AddGlobalVariable("ListDouble", Types.DoubleList);
   AddGlobalVariable("path", Types.String, @"c:\\dell\\Search_level_Robot.txt");

}

function Evaluate()
//Владимир
{
    int Period_int =  (int)Period;
    double High=Input.High[2];      // Переменная хранения значения хая для сравнения
    double Low=Input.Low[2];      // Переменная хранения значения хая для сравнения
    double Hx=0;
    double Lx=0;
    Direction=0;
    string Model="нет";

if ((MaxIndex - CurrentIndex) > Period_int) return;

if (CurrentIndex == MaxIndex)
   {
//////// Описываем модель на покупку
//модель 1
   double Low2=Input.Low[2]+gap;
   if(Input.Low[0] ==Input.Low[2] && (Input.Low[0]<=Input.Low[1] && Low2>=Input.Low[1]))
   {
      for(var x=3; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 1";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//модель 2
   if(Input.Low[0] ==Input.Low[1] && Input.Low[0] ==Input.Low[2] 
   && Input.Low[0] > Input.Low[3] && Input.Low[0] < Input.Close[3] && Input.Low[0] < Input.Open[3] )
   {
      for(var x=4; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 2 (простой ложный пробой)";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//модель 3
   if(Input.Low[0] ==Input.Low[1] && Input.Low[0] ==Input.Low[2]
    && Input.Low[0] > Input.Close[3] && Input.Low[0] < Input.Open[3]  && Input.Low[0] < Input.Close[4])
   {
      for(var x=5; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 3 (сложный ложный пробой)";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//////// Описываем модель на продажу
//модель 1
   double High2=Input.High[2]-gap;
   if(Input.High[0] ==Input.High[2] && (Input.High[0]>=Input.High[1] && High2<=Input.High[1]))
   {
      for(var x=3; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Hx=High;
                     if( High>0)
               {
               Model="Шорт - 1";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//модель 2
   if(Input.High[0] ==Input.High[1] && Input.High[1] ==Input.High[2] 
   && Input.High[0] < Input.High[3] && Input.High[0] > Input.Close[3] && Input.High[0] > Input.Open[3] )
   {
      for(var x=5; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )
               {
                    Hx=High;
                     if( High>0)
               {
               Model="Шорт - 2 (простой ложный пробой)";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//модель 3
   if(Input.High[0] ==Input.High[1] && Input.High[0] ==Input.High[2]
    && Input.High[0] > Input.Close[3] && Input.High[0] < Input.Open[3]  && Input.High[0] < Input.Close[4])
   {
      for(var x=5; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )                
                 {
                    Hx=High;
                     if( High>0)
               {
               Model="Шорт - 3 (сложный ложный пробой)";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//////////////////////////////////
                 
      using (System.IO.StreamWriter sw = System.IO.File.CreateText(path))
      {
         sw.WriteLine("Модель - " + Model);
         sw.WriteLine("Направление - " + Convert.ToString(Direction ));
         sw.WriteLine(string.Join("\r\n", ListDouble ));
         sw.Close(); sw.Dispose();
      }
 
   if (Direction>0 && (Convert.ToBoolean(Enable_Recalculation)==true))
   {   //Открываем позицию вконце формирования свечи с индексом[0] (за 30 секунд до закрытия свечи)
   Levels[0].Level = ListDouble[0];
   }
   //else
   //{Levels[0].Level=0;}
   
}//off if (CurrentIndex == MaxIndex)
 
}


Индиеатор формирует линиию с задержкой на одну свечу (тестовый)

Код: Выделить всё

function Initialize()
{
// Обязательные параметры:
    IndicatorName = "Search_level";   // Задайте название индикатора и сохраните с данным именем
   PriceStudy = true;   // Рисовать в области цены (true – да, false – нет)
   AddInput("Input", Inputs.Candle);   // Input - входной ряд (Inputs.Price) или свечи (Inputs.Candle)

   AddSeries("Last1", DrawAs.Line, Color.Red);// Задаем вид линии индикатора с именем ряда Last
    AddLevel(0, Color.Red, LineStyles.Dot, 2, "Last");
   /* AddLevel(1, Color.Red, LineStyles.Dot, 2, "Last");
    AddLevel(2, Color.Red, LineStyles.Dot, 2, "Last");
    AddLevel(3, Color.Red, LineStyles.Dot, 2, "Last");
    AddLevel(4, Color.Red, LineStyles.Dot, 2, "Last");
    AddLevel(5, Color.Red, LineStyles.Dot, 2, "Last");*/
   
   AddSeries("Direction");                     // Направление открываемой позиции (0 - нет направления, 1- лонг, 2- шорт)
   // AddSeries("GetPriceStep_ind");            // Минимальный шаг цены получаемый с робота (число знаков после запятой)
   AddParameter("GetPriceStep_ind", 2);            // Минимальный шаг цены (число знаков после запятой)
   AddParameter("Period", 200);                  // Период построения уровней

   AddGlobalVariable("path", Types.String, @"c:\\dell\\Search_level.txt");
   AddGlobalVariable("ListDouble", Types.DoubleList);

}

function Evaluate()
//Владимир
{
    int Period_int =  Period-0;
    double max_stop=Math.Round((Input.High[0]*0.2/100),(GetPriceStep_ind+0));
    double gap=Math.Round((max_stop*0.2),(GetPriceStep_ind+0));
    double High=Input.High[3];      // Переменная хранения значения хая для сравнения
    double Low=Input.Low[3];         // Переменная хранения значения хая для сравнения
    double Hx=0;
    double Lx=0;
    Direction=0;
    string Model="нет";

if ((MaxIndex - CurrentIndex) > Period_int) return;

if (CurrentIndex == MaxIndex)
   {
//////// Описываем модель на покупку
//модель 1
   double Low2=Input.Low[3]+gap;
   if(Input.Low[1] ==Input.Low[3] && (Input.Low[1]<=Input.Low[2] && Low2>=Input.Low[2]))
   {
      for(var x=4; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 1";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//модель 2
   if(Input.Low[1] ==Input.Low[2] && Input.Low[1] ==Input.Low[3] 
   && Input.Low[1] > Input.Low[4] && Input.Low[1] < Input.Close[4] && Input.Low[1] < Input.Open[4] )
   {
      for(var x=5; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 2 (простой ложный пробой)";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//модель 3
   if(Input.Low[1] ==Input.Low[2] && Input.Low[1] ==Input.Low[3]
    && Input.Low[1] > Input.Close[4] && Input.Low[1] < Input.Open[4]  && Input.Low[1] < Input.Close[5])
   {
      for(var x=6; x<Period_int;  x++ )
         {
            if ((Low==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Lx=Low;
                     if( Low>0)
               {
               Model="Лонг - 3 (сложный ложный пробой)";
               Direction=1;
                ListDouble.Add(Lx);
               }
            }
          }
   }

//////// Описываем модель на продажу
//модель 1
   double High2=Input.High[3]-gap;
   if(Input.High[1] ==Input.High[3] && (Input.High[1]>=Input.High[2] && High2<=Input.High[2]))
   {
      for(var x=4; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )
               {
                 Hx=High;
                     if( High>0)
               {
               Model="Шорт - 1";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//модель 2
   if(Input.High[1] ==Input.High[2] && Input.High[1] ==Input.High[3] 
   && Input.High[1] < Input.High[4] && Input.High[1] > Input.Close[4] && Input.High[1] > Input.Open[4] )
   {
      for(var x=6; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )
               {
                    Hx=High;
                     if( High>0)
               {
               Model="Шорт - 2 (простой ложный пробой)";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//модель 3
   if(Input.High[1] ==Input.High[2] && Input.High[1] ==Input.High[3]
    && Input.High[1] > Input.Close[4] && Input.High[1] < Input.Open[4]  && Input.High[1] < Input.Close[5])
   {
      for(var x=6; x<Period_int;  x++ )
         {
            if ((High==Input.High[x])||(Low==Input.Low[x]) )                
                 {
                    Hx=High;
                     if( High>0)
               {
               Model="Шорт - 3 (сложный ложный пробой)";
               Direction=2;
                ListDouble.Add(Hx);
               }
            }
          }
   }

//////////////////////////////////
                 
      using (System.IO.StreamWriter sw = System.IO.File.CreateText(path))
      {
         sw.WriteLine("Модель - " + Model);
         sw.WriteLine("Направление - " + Convert.ToString(Direction ));
         sw.WriteLine(string.Join("\r\n", ListDouble ));
         sw.Close(); sw.Dispose();
      }
 if (Direction>0)
 {
 Levels[0].Level = ListDouble[0];
 }
 
   }//off if (CurrentIndex == MaxIndex)
   
}

Автоматизированная торгавля по данному индикатору оказалась невозможна по причине описанной выше

High Profit Trader
Сообщения: 77
Зарегистрирован: 23 мар 2018, 10:54
Поблагодарили: 2 раза

Re: Пытаемся открыть поцицию на последних 30 секундах формирования свечи

Непрочитанное сообщение High Profit Trader » 06 авг 2019, 19:07

У А-Д 4 логическая линия роботов весьма жесткая.
С одной стороны это плохо.
С другой, они же не просто выбрали такую логическую линию. Все эти экзерсайзы с попытками подобрать какую-то логику под абсолютно случайный график котировок были много кратно пройдены профессионалами рынка. А ручная торговля прошла даже многовековое осмысление. И путь рабочий им ясен, он и лежит в логической линии. И то, что многие любители роботов продолжают решать для себя экзерсайзы, чтобы на опыте своего долбления об стену познать незыблемость законов математики, - не было целью у Альфы. Они все же делали механизм роботов для прагматичной торговли, а не для поиска иллюзорных философских камней.


Вернуться в «Общие вопросы по разработке»

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 12 гостей