Общие вопросы по разработке > Как получить данные из индикатора в робот
- evge
- Администратор
- Сообщения: 1812
- Зарегистрирован: 04 фев 2016, 09:46
- Откуда: Млечный путь, планета Земля
- Благодарил (а): 83 раза
- Поблагодарили: 367 раз
- Контактная информация:
Re: Как получить данные из индикатора в робот
Владимир писал(а):Ошибок в индикаторе или в роботе?
Ошибка 1. В индикаторе. Рисует только на последнем баре CurrentIndex == MaxIndex.
Ошибка 2. В стратегии: Правило 2. CloseShort(); Должно быть EnterShort();
Ошибка 3. В стратегии: Правило 1. StopLoss(0.1, SignalPriceType.Price); Должно быть StopLoss(0.1, SignalPriceType.DeltaInPercentFromAveragePrice);
Ошибка 4. В стратегии: Правило 1. MY.WolfeWave(Input1, 326, 2).GetValue("NaprTrenda", 0) >= PowerTrenda должно быть MY.WolfeWave(Input1, 326, 2).GetValue("PowerTrenda", 0) >= PowerTrenda
никогда такого не было и вот опять
-
- Сообщения: 84
- Зарегистрирован: 14 ноя 2016, 02:17
- Благодарил (а): 3 раза
- Поблагодарили: 5 раз
Re: Как получить данные из индикатора в робот
Если я исправлю
то я столкнусь с проблемой рисования индикатора которую исправил пользуясь советом: viewtopic.php?f=27&t=193
Я думаю если этот код вынести за пределы
может вы и правы! Но одного раза, вызова при перерисовке индикатора, производить вычисления вполне достаточно для данной стратегии.
Вот другие ошибки да это надо исправлять немедленно. Спасибо! Буду думать дальше.
Ошибка 1. В индикаторе. Рисует только на последнем баре CurrentIndex == MaxIndex.
то я столкнусь с проблемой рисования индикатора которую исправил пользуясь советом: viewtopic.php?f=27&t=193
Я думаю если этот код вынести за пределы
Код: Выделить всё
if (CurrentIndex == MaxIndex){
}
может вы и правы! Но одного раза, вызова при перерисовке индикатора, производить вычисления вполне достаточно для данной стратегии.
Вот другие ошибки да это надо исправлять немедленно. Спасибо! Буду думать дальше.
- evge
- Администратор
- Сообщения: 1812
- Зарегистрирован: 04 фев 2016, 09:46
- Откуда: Млечный путь, планета Земля
- Благодарил (а): 83 раза
- Поблагодарили: 367 раз
- Контактная информация:
Re: Как получить данные из индикатора в робот
Вот так работают стратегии в АД4, на каждом OnUpdate() не выполняется повторно вызов индикаторов.
Стратегия просто читает значения в истории по рядам которые вы запрашиваете.
А индикатор у Вас рисует только на последнем баре свое значение для
т.е. прочитать предыдущие значения для истории не сможет, поэтому тестирование и не работает. (проверял, сохраняя при тестировании стратегии значения ваших рядов в Log файл, где увидел что индикатор вызывался всего 4 раза вместо ожидаемых 2000*4)
Вот робот скорее всего работать будет (не проверял)
Стратегия просто читает значения в истории по рядам которые вы запрашиваете.
А индикатор у Вас рисует только на последнем баре свое значение для
Код: Выделить всё
AddSeries("NaprTrenda"); // Направление движения цены 0- нет; 1-лонг; 2-шорт; (переменная для робота)
AddSeries("PowerTrenda"); // Сила тренда, коррекция
т.е. прочитать предыдущие значения для истории не сможет, поэтому тестирование и не работает. (проверял, сохраняя при тестировании стратегии значения ваших рядов в Log файл, где увидел что индикатор вызывался всего 4 раза вместо ожидаемых 2000*4)
Вот робот скорее всего работать будет (не проверял)
никогда такого не было и вот опять
-
- Сообщения: 84
- Зарегистрирован: 14 ноя 2016, 02:17
- Благодарил (а): 3 раза
- Поблагодарили: 5 раз
Re: Как получить данные из индикатора в робот
Упростил задачу до минимума код робота
код индикатора
работает открывает позицию и в лонг и шорт
может просто условия по рынку без тренда не подходят?
А может косяк в индикаторе буду индикатор ещё раз пересматривать.
А также искать трендовые движения на других инструментах.
Код: Выделить всё
/**
Открытие позиции происходит по изгзагу
Developed by Владимир;
Algorithm = ТРЕНД;
Hash code 379EBD9768288E896EB42B93032447AE
**/
function Initialize()
{
StrategyName = "IndTrenda";
AddParameter("PowerTrenda", 5, "", 1);
AddInput("Input1", Inputs.Candle, 5, true, "RIH7=ФОРТС");
LongLimit = 1;
ShortLimit = -1;
//AddChartIndicator("MY.WolfeWave", new Dictionary <string, double>{{"Scan", 326},{"NRepetition", 1}});
}
function OnUpdate()
{
/// ПРАВИЛО 1
if ( (MY.Test(Input1, 163).GetValue("NaprTrenda", 0) == 1) && (MY.Test(Input1, 163).GetValue("PowerTrenda", 0) >= PowerTrenda) )
{
EnterLong();
StopLoss(0.1, SignalPriceType.DeltaInPercentFromAveragePrice);
}
/// ПРАВИЛО 2
if ( (MY.Test(Input1, 163).GetValue("NaprTrenda", 0) == 2) && (MY.Test(Input1, 163).GetValue("PowerTrenda", 0) >= PowerTrenda) )
{
EnterShort();
StopLoss(0.1, SignalPriceType.DeltaInPercentFromAveragePrice);
}
}
код индикатора
Код: Выделить всё
function Initialize()
{
// Область определения параметров индикатора
// Обязательные параметры:
IndicatorName = "Test"; // Задайте название индикатора и сохраните с данным именем
PriceStudy = true; // Рисовать в области цены (true – да, false – нет)
AddInput("Input", Inputs.Candle); // Input - входной ряд (Inputs.Price) или свечи (Inputs.Candle)
// Дополнительные параметры:
AddParameter("Scan", 163, 1); // сканируемый период
AddSeries("NaprTrenda"); // Направление движения цены 0- нет; 1-лонг; 2-шорт; (переменная для робота)
AddSeries("PowerTrenda"); // Сила тренда, коррекция
}
function Evaluate()
{
if (Input.Open[0]<Input.Close[2])
{
NaprTrenda=2;
PowerTrenda=60;
}
else
{
NaprTrenda=1;
PowerTrenda=60;
}
}
работает открывает позицию и в лонг и шорт
может просто условия по рынку без тренда не подходят?
А может косяк в индикаторе буду индикатор ещё раз пересматривать.
А также искать трендовые движения на других инструментах.
-
- Сообщения: 84
- Зарегистрирован: 14 ноя 2016, 02:17
- Благодарил (а): 3 раза
- Поблагодарили: 5 раз
Re: Как получить данные из индикатора в робот
Данный пример просто для понятия правильности направления передаются данные или нет.
- Вложения
-
- test робота.jpg (102.53 КБ) 20661 просмотр
- evge
- Администратор
- Сообщения: 1812
- Зарегистрирован: 04 фев 2016, 09:46
- Откуда: Млечный путь, планета Земля
- Благодарил (а): 83 раза
- Поблагодарили: 367 раз
- Контактная информация:
Re: Как получить данные из индикатора в робот
Владимир писал(а):работает открывает позицию и в лонг и шорт
Это говорит что стратегия исправлена и работает, индикатор test работает, а индикатор WolfeWave нет.
В индикаторе test значения в серии подставляются на всей истории, в WolfeWave только в последней точке.
Убрав if (CurrentIndex == MaxIndex) в WolfeWave тоже заработает. Но сам индикатор на графике будет смотреться некрасиво.
никогда такого не было и вот опять
-
- Сообщения: 84
- Зарегистрирован: 14 ноя 2016, 02:17
- Благодарил (а): 3 раза
- Поблагодарили: 5 раз
Re: Как получить данные из индикатора в робот
В индикаторе вынес за пределы if (CurrentIndex == MaxIndex){}
все равно не работает возможно данные из массивов теряются при выходе из if (CurrentIndex == MaxIndex)
буду побывать глобальные переменные вводить.
Код: Выделить всё
function Initialize()
{
// Область определения параметров индикатора
// Обязательные параметры:
IndicatorName = "WolfeWave"; // Задайте название индикатора и сохраните с данным именем
PriceStudy = true; // Рисовать в области цены (true – да, false – нет)
AddInput("Input", Inputs.Candle); // Input - входной ряд (Inputs.Price) или свечи (Inputs.Candle)
AddSeries("LineHigh", DrawAs.Custom, Color.Green); // Задаем вид линии индикатора с именем LineHigh
AddSeries("LineLow", DrawAs.Custom, Color.Red); // Задаем вид линии индикатора с именем LineLow
AddSeries("MarkerUp", DrawAs.Custom, Color.Red); // Метим экстремум
AddSeries("MarkerLow", DrawAs.Custom, Color.Yellow); // Метим экстремум
AddSeries("ChHigh", DrawAs.Custom, Color.Red, true, Axes.Parent); //Рисуем канал внешней свечки для выделения внутренних свечей
AddSeries("ChLow", DrawAs.Custom, Color.Red, true, Axes.Parent); //ChHigh- верхняя линия, ChLow- нижняя линия канала
// Дополнительные параметры:
AddParameter("Scan", 326, 1); // Сканируемый период
//AddParameter("имя переменной", период, множитель), требующий размер истории 163 баров ( т.е. 163*1)
AddParameter("NRepetition", 2); // Колличество повторений тренда
//AddParameter("NTeste", 2); // Колличество повторных входов
// Вывод данных
AddSeries("PointInput"); // Выводим значение предпологаемой переменной цены покупки (переменная для робота)
AddSeries("NaprTrenda"); // Направление движения цены 0- нет; 1-лонг; 2-шорт; (переменная для робота)
AddSeries("PowerTrenda"); // Сила тренда, коррекция
AddSeries("StopExst"); //Значение экстремума для выставления стопа (либо рассчетный или экстремум, что оптимальней?)
}
function Evaluate()
{
int ExstremaNumber = (int)(Scan/5); //Задаём колличество экстремумов
double [] Buf_High = new double[ExstremaNumber]; // Объявление массивов цен (под буферы индикатора)
double [] Buf_Low = new double[ExstremaNumber]; // Объявление массивов цен (под буферы индикатора)
int [] Buf_time_High = new int[ExstremaNumber]; // Объявление массивов время цены (под буферы индикатора)
int [] Buf_time_Low = new int[ExstremaNumber]; // Объявление массивов время цены (под буферы индикатора)
if ((MaxIndex - CurrentIndex) > Scan) return;
{
if (CurrentIndex == MaxIndex)
{
int IzNapr=0; // Изменение направления 0- нет; 1-лонг; 2-шорт;
int NaprHelp=1; // Вспомогательный маркер изменения направления
int Xx=Scan-1; // переменная сравнения номер свечи
int XHighN=Scan-1; // Переменная хранения номера свечи хая для сравнения
int XLowN=Scan-1; // Переменная хранения номера свечи лоу для сравнения
int XhiPostr=0; // Переменная начало данных в массиве для обработки и построения хай
int XloPostr=0; // Переменная начало данных в массиве для обработки и построения лоу
double HighX= Input.High[Scan]; // Переменная хранения значения хая для сравнения
double LowX=Input.Low[Scan]; // Переменная хранения значения лоу для сравнения
double High = Input.High[Scan]; // Переменная сравнения хая
double Low = Input.Low[Scan]; // Переменная сравнения лоу
for (var x= Scan-1; x>0; x--)
{
///// При нормальных свечах
if (Input.Open[x]<Input.Close[x]) // Проверяем закрытие свечи лонг шорт
{// Лонг
if (High<Input.Close[x])
{ // Считаем, что произошло обновление High. Поэтому переписываея значения хая и лоу
IzNapr=1; //лонг
High=Input.High[x];
Low=Input.Low[x];
Xx=x; // Сохраняем значение для построения канала
HighX=High; // Сохраняем значение хая в памяти
XHighN=x; // Сохраняем значение в памяти
}
}
else
{// Шорт
if (Low>Input.Close[x])
{ // Считаем, что произошло обновление low. Поэтому переписываея значения хая и лоу
IzNapr=2; //шорт
High=Input.High[x];
Low=Input.Low[x];
Xx=x; // Сохраняем значение для построения канала
LowX=Low; // Сохраняем значение лоу в памяти
XLowN=x; // Сохраняем значение в памяти
}
}
///// При формировании свечей с гепами
if (Input.Open[x]>Input.Close[x]) //Проверяем закрытие свечи лонг шорт
{// Лонг
if (High<Input.Open[x])
{ // Считаем, что произошло обновление High. Поэтому переписываея значения хая и лоу
IzNapr=1; //лонг
High=Input.High[x];
Low=Input.Low[x];
Xx=x; //Сохраняем значение для построения канала
HighX=High; //Сохраняем значение хая в памяти
XHighN=x; //Сохраняем значение в памяти
}
}
else
{// Шорт
if (Low>Input.Open[x])
{ // Считаем, что произошло обновление low. Поэтому переписываея значения хая и лоу
IzNapr=2; //шорт
High=Input.High[x];
Low=Input.Low[x];
Xx=x; //Сохраняем значение для построения канала
LowX=Low; //Сохраняем значение лоу в памяти
XLowN=x; //Сохраняем значение в памяти
}
}
// Заполняем буфер хаёв
if (IzNapr==NaprHelp && IzNapr==2) // Смена направления с лонга в шорт
{
for (var ch=ExstremaNumber-1; ch>0; ch--)
{
Buf_High[ch]=Buf_High[ch-1];
Buf_time_High[ch]=Buf_time_High[ch-1];
}
Buf_High[0]=HighX;
Buf_time_High[0]=XHighN;
NaprHelp=1;
}
// Заполняем буфер лоёв
if (IzNapr==NaprHelp && IzNapr==1) // Смена направления с шорта в лонг
{
for (var Lo=ExstremaNumber-1; Lo>0; Lo--)
{
Buf_Low[Lo]=Buf_Low[Lo-1];
Buf_time_Low[Lo]=Buf_time_Low[Lo-1];
}
Buf_Low[0]=LowX;
Buf_time_Low[0]=XLowN;
NaprHelp=2;
}
// Строим канал внешней свечи, для выделения внутренних свечей
ChLow[Xx]= Low;
ChLow[0]= Low;
ChHigh[Xx]= High;
ChHigh[0]= High;
ChLow.DrawChannel(ChHigh);
////////
} // Закрытие цикла for
//////// Ищем в массивах начало данных для обработки
for(var a=ExstremaNumber-1; a>0; a--)
{
if (Buf_Low[a]>0 && XloPostr==0)
{XloPostr= a;}
if (Buf_High[a]>0 && XhiPostr==0)
{ XhiPostr= a;}
}
//////// Задаём данные для построения меток на графике MarkerUp.DrawArrowDown(),MarkerLow.DrawArrowUp()
for (var b=0; b<XloPostr+1; b++)
{ if (Buf_Low[b]>0)
MarkerLow[Buf_time_Low[b]]=Buf_Low[b];
} // Данные для построения меток хаёв
for (var c=0; c<XhiPostr+1; c++)
{
if(Buf_High[c]>0)
MarkerUp[Buf_time_High[c]]=Buf_High[c];
} // Данные для построения меток лоёв
///////// Линия тренда
for(var i=0; i<ExstremaNumber-1; i++)
{
if ( Buf_Low[i]>0 && Buf_High[i]>0)
{
LineHigh[Buf_time_Low[i]]=Buf_Low[i];
LineHigh[Buf_time_High[i]]=Buf_High[i];
}
}
///// Построение временной линии - предварительные хай и лоу!!!!!!!!
if (IzNapr==1)// Задаём данные на построение предварительной вершины
{LineLow[Buf_time_Low[0]]=Buf_Low[0];
LineLow[Xx]=High;
}
if (IzNapr==2)// Задаём данные на построение предварительной впадины
{LineLow[Buf_time_High[0]]=Buf_High[0];
LineLow[Xx]=Low;
}
// Данные графика заданы
}// Скобка (CurrentIndex == MaxIndex)
} // Скобка if ((MaxIndex - CurrentIndex) > Scan) return;
/////////////////////////////////
//1 Сравниваем последние значения цены, колличество сравнений заданно переменной "NRepetition", определяем направление тренд переменная "NaprTrenda"
//2 Определим последнее значение хай или лоу, поределяем силу тренда "PowerTrenda"
//3 По данным направления и силе тренда - определяем точку входа (цена входа).
//3.1 Смена направления в сторону тренда (данная свеча неявляется внутренней)
//3.2 Процент коррекции составляет неболее %, задаём в переменной "CorrectionPercentage"
//3.3 Значение экстремума для выставления стопа (либо рассчетный или экстремум, что оптимальней выставляем в //роботе) переменная "StopExst"
NaprTrenda=0; //первоначальный сброс значения тренда
int Repetition = (int)(NRepetition);
if (Repetition>1)// Обязательная проверка, число повторов тренда больше 1 иначе воизбежании ошибки записываем 1
{ //NaprTrenda=0; //первоначальный сброс значения тренда
var RepetitionHigh=0;
var RepetitionLow=0;
for (var i=Repetition; i>0; i--)
{
if ((Buf_High[i-1]>Buf_High[i]) && (Buf_Low[i-1]>Buf_Low[i]))
{RepetitionHigh++;
if (RepetitionHigh==Repetition)
{NaprTrenda=1;}}
if ((Buf_High[i-1]<Buf_High[i]) && (Buf_Low[i-1]<Buf_Low[i]))
{RepetitionLow++;
if (RepetitionLow==Repetition)
{NaprTrenda=2;}}
}
}
else
{ Repetition=1;}
if (Buf_time_Low[0]>Buf_time_High[0])
{ //последний хай //PowerTrenda
if (NaprTrenda==2)
{
PowerTrenda=(1-((Buf_High[0]-Buf_Low[0])/(Buf_High[1]-Buf_Low[0])))*100;
StopExst=Buf_High[0];
}
}
else
{ //последний лоу
if (NaprTrenda==1)
{
PowerTrenda=(1-((Buf_High[0]-Buf_Low[0])/(Buf_High[0]-Buf_Low[1])))*100;
StopExst=Buf_Low[0];
}
}
///////////////////////////////
// Выводим данные на график
MarkerUp.DrawArrowDown();
MarkerLow.DrawArrowUp();
LineHigh.DrawLine(Color.Green, Line.Solid, 2);
LineLow.DrawLine(Color.Red, Line.Solid, 2);
}
все равно не работает возможно данные из массивов теряются при выходе из if (CurrentIndex == MaxIndex)
буду побывать глобальные переменные вводить.
- evge
- Администратор
- Сообщения: 1812
- Зарегистрирован: 04 фев 2016, 09:46
- Откуда: Млечный путь, планета Земля
- Благодарил (а): 83 раза
- Поблагодарили: 367 раз
- Контактная информация:
Re: Как получить данные из индикатора в робот
Не вижу.
Достаточно было закомментировать строку в индикаторе и всё
так
Достаточно было закомментировать строку в индикаторе и всё
Код: Выделить всё
if (CurrentIndex == MaxIndex)
так
Код: Выделить всё
// if (CurrentIndex == MaxIndex)
никогда такого не было и вот опять
-
- Сообщения: 84
- Зарегистрирован: 14 ноя 2016, 02:17
- Благодарил (а): 3 раза
- Поблагодарили: 5 раз
Re: Как получить данные из индикатора в робот
Закомментировал не получается только на графике результат поменялся. всего скорей в массив данные нулевые попадают
Вернуться в «Общие вопросы по разработке»
Кто сейчас на конференции
Сейчас этот форум просматривают: нет зарегистрированных пользователей и 5 гостей