Скачать MetaTrader 5

Советник - invalid handle при обращении к индикатору

Авторизуйтесь или зарегистрируйтесь, чтобы добавить комментарий
ineteye
102
ineteye  

В общем проблемма в том, что индикатор берет данныек из csv файла... все работает без проблемм... Когда начинаю обращаться из советника к этому индикатору ошибки связанные с чтением файла и возвращаемые данные по нулям:

invalid handle 0 in FileClose
invalid handle -1 in FileIsEnding
invalid handle -1 in FileReadString
invalid handle -1 in FileSeek

Где только не смотрел ни где данная проблемма не описыватся может кто сталкивался?????


Вот детально пример:

Индикатор

//+------------------------------------------------------------------+
//|                                               TEST_INDICATOR.mq4 |
//|                                                                  |
//|                                                                  |
//+------------------------------------------------------------------+

#property indicator_chart_window

int handle;
string str;
double Signal[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
//---- indicators
   IndicatorBuffers(1);
   SetIndexBuffer(0, Signal);

//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
//----
   
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
//----
   
   handle = FileOpen("test.txt",FILE_CSV|FILE_READ, ';');
   FileSeek(handle,0,SEEK_SET);
   Signal[0]=StrToDouble(FileReadString (handle));
   FileClose(handle);            
   
   Print(Signal[0]);
//----
   return(0);
  }
//+------------------------------------------------------------------+

Файл test.txt:

999;666

Результат работы идикатора 999 в лог ... Само собой никаких ошибок типа invalid handle нет

Советник:

//+------------------------------------------------------------------+
//|                                                  TEST_EXPERT.mq4 |
//|                                                                  |
//|                                                                  |
//+------------------------------------------------------------------+
double Signal;

int start()
  {
//----
   Signal=iCustom(NULL, 0, "TEST_INDICATOR", 0, 0, 0);
   Print("Данные из файла: "+Signal);
//----
   return(0);
  }
//+------------------------------------------------------------------+


Лог советника:


2011.12.20 00:42:06 2011.12.09 10:01 TEST_INDICATOR: invalid handle -1 in FileClose
2011.12.20 00:42:06 2011.12.09 10:01 TEST_INDICATOR: invalid handle -1 in FileReadString
2011.12.20 00:42:06 2011.12.09 10:01 TEST_INDICATOR: invalid handle -1 in FileSeek
2011.12.20 00:42:04 2011.12.09 10:00 TEST_EXPERT SBER,M5: 0
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR SBER,M5: 0
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR: invalid handle -1 in FileClose
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR: invalid handle -1 in FileReadString
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR: invalid handle -1 in FileSeek
2011.12.20 00:42:04 2011.12.09 10:00 TEST_EXPERT SBER,M5: 0
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR SBER,M5: 0
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR: invalid handle -1 in FileClose
2011.12.20 00:42:04 2011.12.09 10:00 TEST_INDICATOR: invalid handle -1 in FileReadString

Также все три файла в приложении
Файлы:
Yury Reshetov
13491
Yury Reshetov  

Чтобы такой траблы не было, нужно вставлять обязательную проверку на предмет доступности хендла в код:

handle = FileOpen("test.txt",FILE_CSV|FILE_READ, ';');
if (handle > 0) {
   FileSeek(handle,0,SEEK_SET);
   Signal[0]=StrToDouble(FileReadString (handle));
   FileClose(handle);            
   
   Print(Signal[0]);
}
ineteye
102
ineteye  

Спасибо. Ошибка не стала отборажаться, но и из файла чтение тем не менее тоже не происходит.. Вот к примеру такой индикатор передает 1 если

 Signal[i]=1;

А в случае как у меня, то передает 0

.....

2011.12.20 01:19:15 2011.12.09 10:00 TEST_EXPERT SBER,M5: Данные из файла: 0.00000000

2011.12.20 01:19:15 2011.12.09 10:00 TEST_INDICATOR SBER,M5: 0
.....

2011.12.20 01:19:15 2011.12.09 10:00 TEST_INDICATOR SBER,M5: 2147483647


//+------------------------------------------------------------------+
//|                                               TEST_INDICATOR.mq4 |
//|                                                                  |
//|                                                                  |
//+------------------------------------------------------------------+

#property indicator_chart_window

int handle,str;

double Signal[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
//---- indicators
   IndicatorBuffers(1);
   SetIndexBuffer(0, Signal);

//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
//----
   
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
//----
   int Bars_ = Bars - 1;
        int limit,counted_bars = IndicatorCounted();
        //---- проверка на возможные ошибки
        if (counted_bars < 0)
                                    return(-1);
        //---- последний подсчитанный бар должен быть пересчитан
        if (counted_bars > 0)
                                counted_bars--;
        //---- определение номера самого старого бара, 
                                        //начиная с которого будет произедён пересчёт новых баров 
        limit = Bars_ - counted_bars;
        //---- определение номера самого старого бара, 
                                         //начиная с которого будет произедён пересчёт всех баров 
      
   handle = FileOpen("test.txt",FILE_CSV|FILE_READ, ';');
   
   if (handle >= 0) 
   {
      FileSeek(handle,0,SEEK_SET);
      str=StrToDouble(FileReadString (handle));
      FileClose(handle);            
   }


   for (int i=limit;i>=0;i--)
   {
      Print(Signal[i]);
      Signal[i]=str;
   }
   
   
//----
   return(0);
  }
//+------------------------------------------------------------------+
Yury Reshetov
13491
Yury Reshetov  
for (int i=limit;i>=0;i--)
   {
      Print(Signal[i]);
      Signal[i]=str;
   }

Так низя, т.е. сначала считывать для отладки, а потом записывать

Могу дать полезный совет: не пытайтесь поймать сразу двух зайцев, а ловите их поодиночке.

Задача состоит из двух частей: косяк в индикаторе и(ли) косяк в советнике.

Пока не выясните, что косяк не в индикаторе, то никоим образом не сможете выявить наличие косяка в советнике.

Упрощаем задачу, а именно комментрируем в индюке в функции start() всю хрень и оставляем только:

for (int i = limit; i>=0; i--) {
      Signal[i] = 3.14;
}
return(0);

В этом случае, индюк должен отрисовать горизонтальную линию на уровне 3.14. Если отрисовал, значит с буфером индюка все в порядке. Если не так, то ищем косяк.

Теперь пытаемся считать это хозяйство советником. Если советник выдает 3.14, значит в его коде все в порядке. Если не так, то ищем косяк. Если в советнике все в порядке, значит ошибка была в логике индюка.

ineteye
102
ineteye  

Вы меня немного не поняли, я уже подставлял

Signal[i] = 1;

и это передовалось в советник... но когда доходит до данных из файла одни нули.... хотя сам индикатор файл читает и выводит, а как только передаешь в советник

invalid handle

и все идет к тому что не смог открыть файл.. вот собственно и не пойму почему индикатор может получать данные из файла... а когда советник обращается к индикатору invalid handle ... причем массив данных из файла тоже пуст....

Yury Reshetov
13491
Yury Reshetov  
ineteye:

Вы меня немного не поняли, я уже подставлял

и это передовалось в советник... но когда доходит до данных из файла одни нули.... хотя сам индикатор файл читает и выводит, а как только передаешь в советник

invalid handle

и все идет к тому что не смог открыть файл.. вот собственно и не пойму почему индикатор может получать данные из файла... а когда советник обращается к индикатору invalid handle ... причем массив данных из файла тоже пуст....

Черт его знает? Факт что функция start() в индикаторе срабатывает, когда происходит вызов через iCustom(). А почему при таком вызове не происходит открытие файлового хендла, понятия не имею. Это уже наверное вопрос к разработчикам терминала?
ineteye
102
ineteye  
Думаю да ))) У куда мне теперь посоветуешь??? Я в соседнем поссту по 409 билду написал....
Yury Reshetov
13491
Yury Reshetov  
ineteye:
Думаю да ))) У куда мне теперь посоветуешь???
СЮДА
Vladyslav Goshkov
2156
Vladyslav Goshkov  

Сначала попробуйте поправить вызов иКастом() - у Вас туда передается лишний параметр.

//+------------------------------------------------------------------+
//|                                                  TEST_EXPERT.mq4 |
//|                                                                  |
//|                                                                  |
//+------------------------------------------------------------------+
double Signal;

int start()
  {
//----
   Signal=iCustom(NULL, 0, "TEST_INDICATOR", 0, 0, 0);
   Print("Данные из файла: "+Signal);
//----
   return(0);
  }
//+------------------------------------------------------------------+

Поскольку в вызываемом индикаторе нет своих параметров, то после имени индикатора указывается номер буфера и индекс для извлечения значения. То есть, должно быть 2-а параметра, у Вас - 3.

double iCustom( string symbol, int timeframe, string name, ..., int mode, int shift)
Расчет указанного пользовательского индикатора. Пользовательский индикатор должен быть скомпилирован (файл с расширением EX4) 
и находиться в директории каталог_терминала\experts\indicators.
Параметры:
symbol    -     Символьное имя инструмента, на данных которого будет вычисляться индикатор. NULL означает текущий символ.
timeframe         -     Период. Может быть одним из периодов графика. 0 означает период текущего графика.
name      -     Имя пользовательского индикатора.
...       -     Список параметров (при необходимости). Передаваемые параметры должны соответствовать порядку объявления и типу 
внешних (extern) переменных пользовательского индикатора.
mode      -     Индекс линии индикатора. Может быть от 0 до 7 и должен соответствовать индексу, используемому одной из функций SetIndexBuffer.
shift     -     Индекс получаемого значения из индикаторного буфера (сдвиг относительно текущего бара на указанное количество периодов назад).
Пример:
  double val=iCustom(NULL, 0, "SampleInd",13,1,0);
ineteye
102
ineteye  
Спасибо )) поправил, но результат все равно тот же... к тому же я уже писал что с обычной передачей параметров все работает, а вот как доходит до данных из файлов... так все invalid handle
Rashid Umarov
Админ
12700
Rashid Umarov  

Не воспроизводится. Возможны два варианта:

  • каким-то образом мешает UAC
  • вы запускаете эксперта в тестере, в таком случае файл должен лежать в соответствующей папке
12
Авторизуйтесь или зарегистрируйтесь, чтобы добавить комментарий