Библиотеки: Вычисление Z-счета

 

Вычисление Z-счета:

Помогает организовать вычисление Max, Min, матожидание, стандартное отклонение, скос, эксцесс и Z-счет на массиве данных.

Author: MetaQuotes Software Corp.

 
Thanks

Print("Z счет проведенных сделок на аккаунте ",AccountNumber()," равен ",DoubleToStr(getZ(),2));  

this is Z-Score?
 
Yes, it is.
 

Добрый день!

Что-то не правильно считается. Последний элемент массива Array передающегося в функцию GetStatFromSeria(double Array[]), обнуляется.

В коде есть не понятные "движения":

double GetStatFromSeria(double Array[])

{

................................

int W,L,i,size=ArraySize(Array)-1; // - зачем тут мы вычитаем единицу?

...............................

далее смотрим:

ArrayResize(Array,size); // - Это зачем??? Получается тут мы "нарезаем" массив размером меньше, чем перади в функцию
ArrayResize(Seria,size);


size=size+1; // - А это зачем???

ArrayResize(Array,size); // - А это зачем??? А тут мы снова "нарезаем" тот-же размер ??????

ArrayResize(Seria,size);

n=size;


// Из за этих "движений" неправильно считается далее...... .


Max=Array[ArrayMaximum(Array)];
Min=Array[ArrayMinimum(Array)];

 
Это объясняется тем, что я выдирал код из большего по объему скрипта, и не до конца почистил его. Сейчас вроде все неотносящееся к теме удалил. Сверил результаты "старого" и "нового" алгоритма на всякий случай - сходятся. Спасибо за найденный ляп.
 

Еще нашел ошибку :)

for (int cnt=0;cnt<total;cnt++) 
            if (OrderSelect(cnt,SELECT_BY_POS,MODE_HISTORY))
               if (OrderType()==OP_BUY || OrderType()==OP_SELL) counter++; // тут мы отдельно посчитали ордера бай и селл
         double Returns[];
         if (total==0) return;
         ArrayResize(Returns,counter);                                     // тут в соответствии с counter "нарезали" массив Returns
                                                                           // Например: counter = 2, а total= 100.
         for (i=0;i<total;i++)
            if (OrderSelect(i,SELECT_BY_POS,MODE_HISTORY))
               {
               if (OrderType()==OP_BUY || OrderType()==OP_SELL) 
                  {
                  Returns[i]=OrderProfit();                                // тут у нас выбирается ордер, например, с индексом (i) 50 и 99
                                                                           // и записывается в массив  Returns[50] и Returns[100] - таких индексов в массиве нет. Ошибка!
                  }
               }
         }

предлагаю изменить код на следующий:

if (OrdersHistoryTotal()>0)
         {
         int counter=0;
         int i,total=OrdersHistoryTotal();
         double Returns[];
         if (total==0) return;
         //---
         for (i=0;i<=total;i++)
            if (OrderSelect(i,SELECT_BY_POS,MODE_HISTORY))
               {
               if (OrderType()==OP_BUY || OrderType()==OP_SELL) 
                  {
                     ArrayResize(Returns,counter+1);
                     Returns[counter]=OrderProfit();
                     counter++;
                  }
               }
         } 
      Print(" counter = ",counter,", total = ",total);
      res=GetStatFromSeria(Returns);
      if (MathAbs(res)==100000) Print("Z счет не определен!!!");   
      }
Массив Returns - сделать динамическим. И убрать один лишний цикл.
 

Такой еще впрос. Как из Z-Score считается вероятность зависимости (%) ?

 
klot:

Еще нашел ошибку :)


Да, тут действительно был косяк (отмененные отложники сильно подпортили бы расчет). Спасибо. Исправил.
 
klot:

Такой еще впрос. Как из Z-Score считается вероятность зависимости (%) ?

Не удалось добавить код из-за ограничения поразмеру, поэтому прицепил еще один инклюдник NormalProbability.mq4. Для вычисления вероятности используются значения, записанные в массив. Массив был подготовлен с помощью Экселя.
 
Rosh:
klot:

Такой еще впрос. Как из Z-Score считается вероятность зависимости (%) ?

Не удалось добавить код из-за ограничения поразмеру, поэтому прицепил еще один инклюдник NormalProbability.mq4. Для вычисления вероятности используются значения, записанные в массив. Массив был подготовлен с помощью Экселя.


Я тут почитал немного про Z-score и написал функцию:

//+------------------------------------------------------------------+
double fConfidence_limit(double Z_score)
{
   double n_Z=0.398942*MathExp(-(MathPow(Z_score,2)/2.0));
   double Y=1.0/(1+0.2316419*MathAbs(Z_score));
   double N_Z=1-n_Z*((1.330274429*MathPow(Y,5))-(1.821255978*MathPow(Y,4))+(1.781477937*MathPow(Y,3))-(0.356563782*MathPow(Y,2))+(0.31938153*Y));
   if( Z_score<0 ) N_Z=1-N_Z;
   //---
   return((1-((1-N_Z) * 2.0)));
}

В роде как правильно, но не уверен... Посмотри пожалуйста.

Формулу брал тут: http://www.finmarket.net/ru/puc_ar0/

 
klot:


Я тут почитал немного про Z-score и написал функцию:

В роде как правильно, но не уверен... Посмотри пожалуйста.

Формулу брал тут: http://www.finmarket.net/ru/puc_ar0/


Добавил твою функцию в NormalProbability.mq4 и написал простой проверочный скрипт:

//+------------------------------------------------------------------+
//|                                                 CheckNormalF.mq4 |
//|                      Copyright © 2007, MetaQuotes Software Corp. |
//|                                        https://www.metaquotes.net/ru |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2007, MetaQuotes Software Corp."
#property link      "https://www.metaquotes.net/ru"
 
#include <NormalProbability.mqh>
//+------------------------------------------------------------------+
//| script program start function                                    |
//+------------------------------------------------------------------+
int start()
  {
  double val;
  double res1,res2;
//----
   NormalPInitialize();
   for(int i=0;i<302;i++)
      {
      val=i/100.0;
      res1=GetNormalP(val);      
      res2=ProbFunction(val);
      Print("val=",val,"   res1=",DoubleToStr(res1,8),"    res2=",DoubleToStr(res2,8),"  delta=",DoubleToStr(res1-res2,8));
      }
//----
   return(0);
  }
//+------------------------------------------------------------------+
Разница между результатами очень маленькая, обычно не больше 7 знака после запятой, при больших значениях разница ввобще нулевая.

09:30:08 CheckNormalF EURUSD,H1: val=2.26 res1=0.98777557 res2=0. 98808942 delta=-0. 00031385
09:30:08 CheckNormalF EURUSD,H1: val=2.27 res1=0.98839624 res2=0. 98839625 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.28 res1=0.98869619 res2=0. 98869620 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.29 res1=0.98898937 res2=0. 98898938 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.3 res1=0.98898937 res2=0. 98927593 delta=-0. 00028655
09:30:08 CheckNormalF EURUSD,H1: val=2.31 res1=0.98955595 res2=0. 98955596 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.32 res1=0.98955595 res2=0. 98982959 delta=-0. 00027364
09:30:08 CheckNormalF EURUSD,H1: val=2.33 res1=0.99009695 res2=0. 99009695 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.34 res1=0.99035815 res2=0. 99035816 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.35 res1=0.99061331 res2=0. 99061332 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.36 res1=0.99086255 res2=0. 99086255 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.37 res1=0.99110597 res2=0. 99110598 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.38 res1=0.99134369 res2=0. 99134370 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.39 res1=0.99157582 res2=0. 99157583 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.4 res1=0.99180247 res2=0. 99180248 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.41 res1=0.99202374 res2=0. 99202375 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.42 res1=0.99223975 res2=0. 99223975 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.43 res1=0.99245059 res2=0. 99245059 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.44 res1=0.99265637 res2=0. 99265637 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.45 res1=0.99285719 res2=0. 99285719 delta=-0. 00000001
09:30:08 CheckNormalF EURUSD,H1: val=2.46 res1=0.99305314 res2=0. 99305315 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.47 res1=0.99305314 res2=0. 99324434 delta=-0. 00019120
09:30:08 CheckNormalF EURUSD,H1: val=2.48 res1=0.99343087 res2=0. 99343088 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.49 res1=0.99361283 res2=0. 99361284 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.5 res1=0.99379032 res2=0. 99379032 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.51 res1=0.99379032 res2=0. 99396343 delta=-0. 00017311
09:30:08 CheckNormalF EURUSD,H1: val=2.52 res1=0.99413224 res2=0. 99413224 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.53 res1=0.99429685 res2=0. 99429686 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.54 res1=0.99445735 res2=0. 99445736 delta=-0. 00000000
09:30:08 CheckNormalF EURUSD,H1: val=2.55 res1=0.99445735 res2=0. 99461383 delta=-0. 00015648

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