Hatalar, hatalar, sorular - sayfa 2160

 
Andrey Khatimlianskii :

MQ açısından, görünüşe göre, doğru. Her zaman olduğu gibi, daha uygun olduğu için bizim için karar verdik.

Ticaret, otomatik ticaret sistemleri ve ticaret stratejilerinin test edilmesi hakkında forum

Profil mesajları kayboldu.

Renat Fatkhullin , 2018.03.08 10:31

Uyumluluk modunda çalışan işlevsellik miktarını azaltmak için geçici olarak kaldırıldı.

Transfer işlemini bitirir bitirmez yeni özellikler ekleyeceğiz.

Bu yeni, çok büyük ve çok işlevli bir sistemdir.


Yeni sohbetler tanıtılıyor.

 
Andrey Khatimlianskii :

MQ açısından, görünüşe göre, doğru. Her zaman olduğu gibi, daha uygun olduğu için bizim için karar verdik.

Telepatik seviyeye geçelim ...)))))

 

Ana göstergede anlaşılmaz bir hata. Yalnızca H 1'in altındaki zaman dilimlerinde ve yalnızca terminalin başlatıldığı anda gerçekleşir . Metin hatalar "S-v5 (EURUSD,M10) dizisi 'S-v5.mq5' (211.54) içinde aralık dışında". Zaman serisi bayrağı tüm arabellekler için ayarlanmış olsa da, oluşturma doğru şekilde ancak ters sırada gerçekleşir.

Şablonun bileşimi ana göstergedir (No. 1) (bir hatanın meydana geldiği), ek bir göstergedir (No. 2) (ana göstergenin birkaç tutamağını farklı parametrelerle birleştirir (görüntüleme süresi)), bir göstergedir ( 1) numaralı göstergeden gelen sinyallere göre ana çizelgede okları görüntüleyen No. 3), 2 numaralı göstergeden gelen sinyallere göre ana çizelgede okları görüntüleyen gösterge (No. 4).

Zaman çerçevesini değiştirmek, şablonu yeniden uygulamak, 2'den 4'e veya yalnızca 1'in altındaki 2 göstergeyi kaldırırsanız, Piyasa İzleme'den yeni bir sembol görüntüler ve bu şablonu uygularsanız - hata yeniden oluşmaz ve tüm göstergeler doğru çizilir .  

 

Derlerken hata

 #import  "Test1.ex5"
       void f1();
#import  "Test2.dll"
       void f2();
#import
typedef void (*fn)();
void OnStart ()
{
    fn fn1 =        f1; //нормально
    fn fn2 =        f2; //Error: 'f2' - pointer to this function type is not supported yet
    fn fn3 = Test2::f2; //нормально
}
 

Hata mesajı, neden kapsamlı kodda olduğunu netleştirmiyor

 struct A {
     void f( int     ) {}
     void g( int fn ) { f( fn ); } //Error: ')' - unexpected token ???
};
typedef void (*fn)();

aşağıda açık

 struct A {
    void f( int     ) {}
    void g( int fn ) { f( fn ); } //Error: 'fn' - identifier already used
};
struct fn {};
 

Hata mesajı yok

 typedef void (*fn)();
void f( int i ) { Print ( __FUNCTION__ , ":" , i ); }
void OnStart ()
{
    f( fn() );
}

üstelik yürütülür ve hatta sonuç (!)

Bu varyantta:

 typedef int (*fn)();
void OnStart () { Print ( fn() ); }

hata satırına geçiş çalışmıyor (Enter ile)


 

Derlerken hata

    void g(   int ) {}
    void g( uint ) {}
#import "Test.ex5"
     void f(   int );
     void f( uint );
#import
typedef void (*fn1)(   int );
typedef void (*fn2)( uint );
void OnStart ()
{
    fn1 g1 = g; /*нормально и результат*/ g1( 1 ); //совпадает с ожидаемым
    fn2 g2 = g; /*нормально и результат*/ g2( 1 ); //совпадает с ожидаемым
    fn1 f1 = f; //Error: 'f' - cannot resolve function address
    fn2 f2 = f; /*нормально и результат*/ f2( 1 ); //совпадает с ожидаемым
                                                   //при наличии Test.ex5
}
 

İşi hızlandırmak amacıyla, bu örneği oluşturduğumda, yanlışlıkla rafa koyduğum bir tuhaflıkla karşılaştım.

Ve şimdi, bu tuhaflıkla başa çıkmaya çalıştığımda kafam daha da karıştı.

Bu yüzden hesaplamada, bir çift dizi oluşturarak atlamaya karar verdiğim sqrt() karekök işlevini kullanıyorum.

Çünkü Her zaman tam sayıların karekökünü alırım, ardından bir dizi oluşturmak şöyle görünür:

   double SQRT[];
   int ss=Width*Width+Height*Height;
   ArrayResize (SQRT,ss);
   for ( double w= 0 ;w<ss;w++) SQRT[( int )w]= sqrt (w);

SQRT[x] dizisinden okumanın sqrt(x) işlevinden daha hızlı olduğunu varsaymak mantıklıdır.
Ve bu, doğrulama koduyla onaylanır:

   double Sum1= 0 ,Sum2= 0 ;
   ulong t= GetMicrosecondCount ();
   for ( int i= 0 ;i<ss;i++) Sum1+= sqrt ( double (i));   // Находим сумму квадратных корней всех целых чисел от 0 до ss
   t= GetMicrosecondCount ()-t;
   Print ( "Время на сумму " + IntegerToString (ss)+ " значений функций = " + IntegerToString (t)+ " мкс, Сумма = " + DoubleToString (Sum1));
   t= GetMicrosecondCount ();
   for ( int i= 0 ;i<ss;i++) Sum2+=SQRT[( int )(i)];     // Находим сумму квадратных корней всех целых чисел от 0 до ss через сложение элементов массива SQRT[]
   t= GetMicrosecondCount ()-t;
   Print ( "Время на сумму " + IntegerToString (ss)+ " значений массива = " + IntegerToString (t)+ " мкс, Сумма = " + DoubleToString (Sum2));

sonuç, hızda ~ 1,5 kat bir artış olduğunu gösterir:

Ancak koddaki sqrt() işlevini SQRT[] dizisinin öğelerini okuyarak değiştirdiğimde, işi hızlandırmak yerine korkunç frenler alıyorum.

SQRT[] dizisinden bir öğeyi okumak birçok kez, hatta sqrt() işlevinin yürütülmesinden bir büyüklük sırası daha uzun sürer.

Ve hız sızıntısının nerede olduğunu anlamıyorum. Sonuçta, yukarıdaki doğrulama kodu aksini söylüyor.

Derleyicinin garip bir şekilde büyük bir diziye eriştiği ve döngünün her yinelemesinde diziyi "unuttuğu" ve her seferinde bir tür hizmet indekslemesi gerçekleştirdiği varsayılabilir.

Ancak bu, dahili bir mantıksal veya stratejik derleyici hatasıdır. Ayrıca, bununla açıkça bir şeyler yapılmalı, tk. bu hız sızıntısı çok önemlidir ve tespit edilmesi zordur. belli değil.

Bu tuhaflığı göstermek için komut dosyası kodunu ekliyorum.

Varsayılan olarak çalıştırıldığında (dizi=yanlış), sqrt() işlevleri değerlendirilir ve dizi doğru olarak değiştirildiğinde, diziden karekök değeri alınır.

SORUN NEDİR? FRENLER NEREDEN?

Dosyalar:
Swirl.mq5  11 kb
 
Nikolai Semko :

İşi hızlandırmak amacıyla, bu örneği oluşturduğumda, yanlışlıkla rafa koyduğum bir tuhaflıkla karşılaştım.


SQRT[x] dizisinden okumanın sqrt(x) işlevinden daha hızlı olduğunu varsaymak mantıklıdır .

Dinamik bir diziden bir gerçek değildir.

Ayrıca, kökü almak uzun zamandır SQRTSD işlemci komutu düzeyinde olmuştur. Yani, dinamik bir dizideki kötü şöhretli erişim maliyetlerinin yardımıyla, işlemci uygulamasını yenmek artık mümkün olmayacak.


Ve bu, doğrulama koduyla onaylanır :

sonuç, hızda ~ 1,5 kat bir artış olduğunu gösterir:

Onaylandığından şüpheliyim.

Bu tür bir kod, döngü optimizasyonu üzerine bir ders kitabından çıktı. Durum çok basit olduğu için kod iyileştirici bundan bir şeyler çıkarabilir:

   for ( int i= 0 ;i<ss;i++) 
      Sum2+=SQRT[i];

Yani, açıkça ideal olarak optimize edilmiş durumların kullanılması durumunda performans ölçümü, testin hedefleriyle açık bir şekilde ilişkilendirilmelidir.

Bu durumda test yanlıştır.

SQRT[] dizisinden bir öğeyi okumak birçok kez, hatta sqrt() işlevinin yürütülmesinden bir büyüklük sırası daha uzun sürer.

Ve hız sızıntısının nerede olduğunu anlamıyorum. Sonuçta, yukarıdaki doğrulama kodu aksini söylüyor.

Son montajcı kodunu görmeden, şuna doğru eğiliyorum:

  1. sqrt aslında hızlıdır (yerel kodda çok verimli bir oluşturucumuz var, sqrt saf SQRTSD'ye dönüşür)
  2. doğrulama kodu çok basit ve optimizasyon ile gecikmeleri telafi ediyor


Kodu dikkatlice kontrol edelim. Gerçek sebebin ne olduğunu öğrenmek ilginç.

SQRTSD — Compute Square Root of Scalar Double-Precision Floating-Point Value
  • www.felixcloutier.com
Computes square root of the low double-precision floating-point value in xmm3/m64 and stores the results in xmm1 under writemask k1. Also, upper double-precision floating-point value (bits[127:64]) from xmm2 is copied to xmm1[127:64].
 
Renat Fatkhullin :

Dinamik bir diziden bir gerçek değildir.


Son montajcı kodunu görmeden, şuna doğru eğiliyorum:

  1. sqrt aslında hızlıdır (yerel kodda çok verimli bir oluşturucumuz var, sqrt saf SQRTSD'ye dönüşür)
  2. doğrulama kodu çok basit ve optimizasyon ile gecikmeleri telafi ediyor

Statik bir dizi denedim - aynı şey.

sqrt kadar hızlı, bu işlevin bir dizi öğesini okumaktan 10 kat daha hızlı olabileceğine inanmakta zorlanıyorum.

Ayrıca, örneğimde tuvalin boyutu küçültülmüşse, diyelim ki 50x50 (bunun için Size bir giriş parametresi var, 0 yerine 50 ayarlamanız gerekiyor),

ve dizi çok daha küçük (5000 eleman) olacak, ardından hız resmi belirgin şekilde değişecektir. Artık böyle güçlü bir kontrast yok.

Ama anlamıyorum, öğelerine erişim hızı dizinin boyutuna mı bağlı?

Ve doğrulama kodunun basitliği hakkında belki de haklısınız.

Biraz karmaşıklaştırmaya çalıştım ve sonuç tamamen farklı:

 for ( int i= 0 ;i<ss;i++) Sum1+= i* sqrt ( double (i));
....
for ( int i= 0 ;i<ss;i++) Sum2+= i* SQRT[( int )(i)];


Neden: