MQL5'te Elliott Dalgalarının Otomatik Analizini Uygulama
Giriş
Piyasa analizinin en popüler yöntemlerinden biri Elliott Dalga Prensibi'dir. Ancak, bu süreç oldukça karmaşıktır; bu da bizi ek enstrümanların kullanımına götürür. Bu enstrümanlardan biri otomatik işaretleyicidir.
Bu makalede, MQL5 dilinde Elliott Dalgalarının otomatik bir analizörünü oluşturma süreci anlatılmaktadır. Okuyucunun dalga teorisi hakkında halihazırda bilgi sahibi olduğu varsayılır; bu konuda bilgi sahibi değilseniz uygun kaynaklara başvurmanız gerekir.
1. Elliott'un Dalga Prensibi
Elliott Dalgaları - Ralph Nelson Elliott tarafından geliştirilen, piyasadaki tüm fiyat hareketlerinin insan psikolojisine tabi olduğu ve dürtü dalgalarının döngüsel bir değişim süreci, düzeltme ve bunun tersi olduğu teorik bir piyasa davranışı modelidir.
Dürtü dalgaları, beş fiyat dalgalanmasından oluşan bir dizi, düzeltme dalgaları üç veya beş fiyat dalgalanmasından oluşan bir dizidir. Biçimleri, yapıları ve bunlara uygulanabilecek kurallar bakımından dürtü dalgaları aşağıdaki türlerdendir:
1. Dürtüler: | |
---|---|
Şekil 1. Dürtü |
|
2. Öncül diyagonal: | |
Şekil 2. Öncül diyagonal |
|
3. Diyagonaller: | |
Şekil 3. Diyagonal |
|
Düzeltme dalgaları şu şekilde sınıflandırılır: | |
4. Zigzaglar: | |
Şekil 4. Zigzag |
|
5. Yassılar: | |
Şekil 5. Yassı |
|
6. İkili Zigzaglar: | |
Şekil 6. İkili Zigzag |
|
7. Üçlü Zigzaglar: | |
Şekil 7. Üçlü Zigzag |
|
8. İkili Üçler: | |
Şekil 8. İkili Üç |
|
9. Üçlü Üçler: | |
Şekil 9. Üçlü Üç |
|
10. Daralan Üçgen: | |
Şekil 10. Daralan Üçgen |
|
11. Genişleyen Üçgenler: | |
Şekil 11. Genişleyen Üçgen |
|
Yukarıda sunulan dalga modelleri ve kuralları, yalnızca dalga analizinin klasik kavramına karşılık gelir.
Ayrıca, Forex piyasasının incelenmesi sırasında oluşan modern anlayışı da vardır. Örneğin, yeni bir eğik (kayan) üçgen modeli bulunur, ikinci dalgadaki üçgen ile dürtüler tanımlanır, vb.
Şekil 1-11'den görülebileceği gibi, her bir dürtü veya düzeltme dalgası, aynı dürtü ve düzeltme dalgalardan (kesik çizgi ile gösterilmiştir) oluşur; ancak bu, daha az derecededir. Bu, Elliott dalgalarının sözde fraktal (yuvalanma) halidir: Büyük dereceli dalgalar, daha düşük dereceli dalgalardan oluşur; bu da sırayla, çok daha az dalgalardan oluşur, vb.
Bu notta, Elliott Dalga Prensibi'ne kısa girişi tamamlayabilir ve dalgaların otomatik olarak işaretlenmesi konusuna geçebiliriz.
2. Elliott Waves'in otomatik işaretleme algoritması
Muhtemelen halihazırda fark etmiş olduğunuz gibi, Elliott Dalga Analizi karmaşık ve çok yönlü bir süreçtir. Bu nedenle, insanlar daha en baştan, onu kolaylaştırmaya yardımcı olacak enstrümanları aramaya ve uygulamaya başladılar.
Böyle bir araç, Elliott Dalgalarının otomatik olarak işaretlenmesi için mekanizma haline geldi.
Otomatik işaretlemenin iki prensibini ayırt edebiliriz:
- Dalgaların fraktalitesine göre, analiz yukarıdan aşağıya, büyükten küçüğe doğru yapılır;
- Analiz, olası tüm seçeneklerin doğrudan numaralandırılmasıyla gerçekleştirilir.
Elliott Dalgalarının otomatik analizinin bir blok diyagramı Şekil 12'de gösterilmiştir.
Şekil 12. Elliott Dalgalarının otomatik analizinin blok diyagramı
Dürtünün otomatik işaretleme örneğine dayanarak algoritmayı daha ayrıntılı olarak düşünün (bkz. Şekil 13).
İlk aşamada, fiyat grafiğinin gerekli zaman aralığında, "Zigzag" kullanılarak, işaretleme yapmak için gerekli olan nokta miktarı vurgulanır. Nokta sayısı, ne tür bir dalgayı analiz etmek istediğimize bağlıdır. Dolayısıyla, Dürtünün analizi için altı nokta gereklidir - 5 tepe noktası ve bir başlangıç noktası. Zigzag'ı analiz ediyor olsaydık, gerekli noktaların sayısı 4 - 3 tepe noktası ve bir başlangıç noktası olurdu.
"Zigzag" fiyat grafiğinde altı nokta belirlediyse, o zaman anında Dürtünün bir işaretlemesini oluşturabiliriz: İlk nokta - birinci dalganın başlangıç noktası, ikinci nokta - birinci dalganın tepe noktası, üçüncü nokta - ikinci dalganın tepe noktası, dördüncü nokta - üçüncü dalganın tepe noktası, beşinci nokta - dördüncü dalganın tepe noktası ve altıncı nokta - beşinci dalganın tepe noktası.
Ancak Şekil 13'te "Zigzag" 8 nokta belirlemiştir. Bu durumda, dalganın tüm olası seçeneklerini ve işaretlemelerini bu noktalara göre numaralandırmak gerekecektir. Ve bunlardan beş tane olacak (farklı renklerle işaretlenmiş). Ve işaretlemenin her bir sürümünün kurallara göre kontrol edilmesi gerekecektir.
Şekil 13. Bir dürtünün işaretlenmesini işaretleme seçenekleri
Kurallara göre kontrol edildikten sonra, dalganın işaretlenmesinin tüm parametreler tarafından bir Dürtü olması durumunda, tüm alt dalgaları aynı şekilde analiz edilir.
Aynısı, diğer tüm dürtü ve düzeltme dalgalarının analizi için de geçerlidir.
3. Otomatik işaretleme için dalga türleri
Daha önce belirtildiği gibi, analiz, belirli bir aralıkta bir dalga bulmak için program talimatlarını vererek yukarıdan aşağıya yapılacaktır. Ancak, en büyük aralıkta, dalganın durumunu, başlangıcını ve sonunu belirlemek imkansızdır. Böyle bir dalgayı başlamamış ve bitmemiş olarak adlandıracağız.
Tüm dalgalar aşağıdaki gruplara ayrılabilir:
- Başlamamış dalgalar:
- Başlamamış birinci dalgaya sahip dalgalar - 1-2-3-4-5 (örneğin, başlamamış dalga 1'e sahip bir Dürtü, gerekli nokta sayısı - 5) ve 1-2 -3 (örneğin, başlamamış A dalgasına sahip bir Zigzag; gerekli nokta sayısı - 3);
- Başlamamış ikinci dalgaya sahip dalgalar - 2-3-4-5 (örneğin, başlamamış dalga 2'ye sahip bir Diyagonal, gerekli nokta sayısı - 4) ve 2-3 (örneğin, başlamamış B dalgasına sahip bir yassı; gerekli nokta sayısı -2);
- Başlamamış üçüncü dalgaya sahip dalgalar - 3-4-5 (örneğin, başlamamış Y dalgasına sahip bir Üçlü Zigzag; gerekli nokta sayısı - 3);
- Başlamamış dördüncü dalgaya sahip dalgalar - 4-5 (örneğin, başlamamış D dalgasına sahip bir Üçgen; gerekli nokta sayısı -2);
- Başlamamış beşinci dalgaya sahip dalgalar - 5 (örneğin, başlamamış bir dalga 5'e sahip bir Dürtü; gerekli nokta sayısı - 1);
- Başlamamış üçüncü dalgaya sahip dalgalar - 3 (örneğin, başlamamış bir Z dalgasına sahip ikili üç; gerekli nokta sayısı - 1);
- Bitmemiş dalgalar:
- Bitmemiş beşinci dalgaya sahip dalgalar - 1-2-3-4-5 (örneğin, bitmemiş dalga 5'e sahip bir Dürtü; gerekli nokta sayısı - 5);
- Bitmemiş dördüncü dalgaya sahip dalgalar - 1-2-3-4> (örneğin, bitmemiş bir XX dalgasına sahip bir Üçlü zigzag; gerekli nokta sayısı - 4);
- Bitmemiş üçüncü dalgaya sahip dalgalar - 1-2-3> (örneğin, bitmemiş dalga 3'e sahip bir öncül diyagonal; gerekli nokta sayısı -3);
- Bitmemiş ikinci dalgaya sahip dalgalar - 1-2> (örneğin, bitmemiş B dalgasına sahip bir Zigzag; gerekli nokta sayısı -2);
- Bitmemiş birinci dalgaya sahip dalgalar - 1> (örneğin, bitmemiş A dalgasına sahip bir yassı; gerekli nokta sayısı -1);
- Başlamamış ve bitmemiş dalgalar:
- Başlamamış birinci dalgaya ve bitmemiş ikinci dalgaya sahip dalgalar -1-2>(örneğin, başlamamış A dalgasına ve bitmemiş B dalgasına sahip bir Zigzag; gerekli nokta sayısı - 1);
- Başlamamış ikinci dalgaya ve bitmemiş üçüncü dalgaya sahip dalgalar - 2-3>(örneğin, başlamamış B dalgası ve bitmemiş C dalgasına sahip bir Zigzag; gerekli nokta sayısı - 1);
- Başlamamış üçüncü dalgaya ve bitmemiş dördüncü dalgaya sahip dalgalar - 3-4>< (örneğin, başlamamış dalga 3'e ve bitmemiş dalga 4'e sahip bir Dürtü; gerekli nokta sayısı - 1);
- Başlamamış dördüncü dalgaya ve bitmemiş beşinci dalgaya sahip dalgalar - 4-5> (örneğin, başlamamış dalga 4'e ve bitmemiş dalga 5'e sahip bir Dürtü; gerekli nokta sayısı - 1);
- Başlamamış birinci ve bitmemiş üçüncü dalgaya sahip dalgalar - 1-2-3>(örneğin, başlamamış W dalgası ve bitmemiş Y dalgasına sahip üçlü üç; gerekli nokta sayısı - 2);
- Başlamamış ikinci dalgaya ve bitmemiş dördüncü dalgaya sahip dalgalar -2-3-4>(örneğin, başlamamış dalga 2'ye ve bitmemiş dalga 4'e sahip bir öncül diyagonal; gerekli nokta sayısı - 2);
- Başlamamış üçüncü dalgaya ve bitmemiş beşinci dalgaya sahip dalgalar - 3-4-5>(örneğin, başlamamış dalga 3'e ve bitmemiş dalga 5'e sahip bir Diyagonal; gerekli nokta sayısı - 2);
- Başlamamış birinci dalgaya ve bitmemiş dördüncü dalgaya sahip dalgalar -1-2-3-4>(örneğin, başlamamış W dalgasına ve bitmemiş XX dalgasına sahip üçlü üç; gerekli nokta sayısı - 3);
- Başlamamış ikinci dalgaya ve bitmemiş beşinci dalgaya sahip dalgalar - 2-3-4-5 (örneğin, başlamamış dalga 2'ye ve bitmemiş dalga 5'e sahip bir Dürtü; gerekli nokta sayısı - 3);
- Başlamamış birinci dalgaya ve bitmemiş beşinci dalgaya sahip dalgalar -1-2-3-4-5>(örneğin, başlamamış W dalgasına ve bitmemiş Z dalgasına sahip bir Üçlü zigzag; gerekli nokta sayısı - 4);
- Tamamlanmış dalgalar - 1-2-3-4-5 (gerekli nokta sayısı - 6) ve 1-2-3 (gerekli nokta sayısı - 4).
Dalga sayısından sonraki "<" işareti, dalganın başlamadığını gösterir. Dalga sayısından sonraki ">" işareti, dalganın bitmediğini gösterir.
Şekil 14'te aşağıdaki dalgaları görebiliriz:
- Başlamamış birinci dalga A -A -B-C'ye sahip dalga;
- Başlamamış ilk W'ye sahip dalga ve bitmemiş ikinci X dalgası -W<-X>;
- Tamamlanmış dalga B ve C;
Şekil 14. Başlamamış ve bitmemiş dalgalar
4. Elliott Dalgalarının otomatik analizörünün veri yapılarının açıklaması
Elliott Dalgalarının otomatik analizörünü yazmak için aşağıdaki veri yapılarına ihtiyacımız olacak:
4.1. Programda analiz edilen dalgaların açıklamasının yapısı:
// The structure of the description of the analyzed waves in the program struct TWaveDescription { string NameWave; // name of the wave int NumWave; // number of sub-waves in a wave string Subwaves[6]; // the names of the possible sub-waves in the wave };
4.2. Belirli bir dalganın parametrelerini depolamak için bir sınıf:
// A class for storing the parameters of a wave class TWave { public: string Name; // name of the wave string Formula; // the formula of the wave (1-2-3-4-5, <1-2-3 etc.) int Level; // the level of the wave double ValueVertex[6]; // the value of the top of the wave int IndexVertex[6]; // the indexes of the top of the waves };
4.3. Zigzag'ın tepe noktalarının değerlerinive tepe noktalarının indekslerini depolamak için bir sınıf:
// A class for storing the values of vertexes and indexes of the zigzag class TZigzag:public CObject { public: CArrayInt *IndexVertex; // indexes of the vertexes of the zigzag CArrayDouble *ValueVertex; // value of the vertexes of the zigzags };
4.4. Dalga ağacını temsil edecek sınıf:
// A class for the presentation of the tree of the waves class TNode:public CObject { public: CArrayObj *Child; // the child of the given tree node TWave *Wave; // the wave, stored in the given tree node string Text; // text of the tree node TNode *Add(string Text,TWave *Wave=NULL) // the function of adding the node to the tree { TNode *Node=new TNode; Node.Child=new CArrayObj; Node.Text =Text; Node.Wave=Wave; Child.Add(Node); return(Node); } };
4.5. Zigzag tarafından bulunan noktaları depolamak için yapı:
// The structure for storing the points, found by the zigzag struct TPoints { double ValuePoints[]; // the values of the found points int IndexPoints[]; // the indexes of the found points int NumPoints; // the number of found points };
4.6. Grafiğin önceden analiz edilmiş bölümünün parametrelerini depolamak için bir sınıf:
// A class for storing the parameters of the already analyzed section, corresponding to the wave tree node class TNodeInfo:CObject { public: int IndexStart,IndexFinish; // the range of the already analyzed section double ValueStart,ValueFinish; // the edge value of the already analyzed section string Subwaves; // the name of the wave and the group of the waves TNode *Node; // the node, pointing to the already analyzed range of the chart };
4.7. Grafiğe yerleştirmeden önce dalgaların işaretini depolamak için bir sınıf:
// A class for storing the marking of waves before placing them on the chart class TLabel:public CObject { public: double Value; // the value of the vertex int Level; // the level of the wave string Text; // the marking of the wave };
5. Elliott Dalgalarının otomatik analizörünün işlevinin açıklaması
Elliott Dalgalarının otomatik analizörünü yazmak için aşağıdaki işlevlere ihtiyacımız olacak:
int Zigzag(intH,int Start,int Finish,CArrayInt *IndexVertex,CArrayDouble *ValueVertex)
Elliott Dalgalarının otomatik analizöründeki önemli bir öğe, dalgaların oluşturulacağı "Zigzag"dır. Herhangi bir parametre ile "Zigzag" hesaplaması çok hızlı yapılmalıdır.
Analizörümüzde, "Yeniden Çizilmeyen ZigZaglar Nasıl Hızlı Bir Şekilde Yazılır?" makalesinden alınan "Zigzag"ı kullanacağız.
Zigzag işlevi, Zigzag'ı Başlangıç'tan Bitiş'e kadar olan aralıkta H parametresiyle hesaplar ve ardından sırasıyla tepe noktalarının bulunan indekslerini ve tepe noktalarınındeğerlerini adresleri bu işleve iletilen IndexVertex ve ValueVertex dizilerine kaydeder.
Zigzag işlevi, "Zigzag"ın bulunan tepe noktalarının sayısını döndürür.
"Zigzag" doldurma işlevi ve parametrelerinin depolanması:
void FillZigzagArray(int Start,int Finish)
Daha önce gösterildiği gibi, dalganın işaretlenmesi için fiyat grafiğinde gerekli sayıda noktayı bulmamız gerekecek. Bu nedenle, daha sonra bu noktaları bulmak için yineleyeceğimiz farklı parametrelerle "Zigzag"ın tepe noktası dizisine ihtiyacımız olacak.
FillZigzagArray işlevi, H parametresinin tüm olası değerleriyle birlikte grafiğin Başlangıcından Bitişine kadar olan aralığındaki "Zigzag"ıhesaplar ("Zigzag"ın tepe noktası sayısı ikiye eşit olmayana veya ikiden az olmayana kadar), bulunan tepe noktaları hakkındaki bilgileri TZigzag sınıfının nesnelerinde depolar ve bu nesneleri, açıklaması aşağıdaki gibi olan genel ZigzagArray dizisine kaydeder:
CArrayObj *ZigzagArray;
Belirtilen aralıktaki arama işlevi, fiyat grafiğindeki noktaların sayısını gerektirir:
bool FindPoints(int NumPoints,int IndexStart,int IndexFinish,double ValueStart,double ValueFinish,TPoints &Points)
FindPoints işlevi, fiyat grafiğinde IndexStart'tan IndexFinish'e kadar olan gerekli aralıkta ilk ve son nokta olan ValueStart ve ValueFinish'in gerekli değerleriyle enaz üç NumPoints noktası arar ve bunları (yani noktaları) bağlantısı bu işleve iletilen Noktaların yapısına kaydeder.
FindPoints işlevi, gerekli nokta sayısı bulunursa true değerini, aksi takdirde false değerini döndürür.
5.4. NotStartedAndNotFinishedWaves
Başlamamış ve bitmemiş dalgaların analizinin işlevi:
void NotStartedAndNotFinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level)
NotStartedAndNotFinishedWaves işlevi, üçüncü dalga grubunun tüm dalgalarını - başlamamış ve bitmemiş - analiz eder. İşlev, NumWave dalgasını (dalga seviyesi Düzeyi ile), alt dalga dalgaları biçimini (bir Zigzag, düz, İkili zigzag ve (veya) vb. biçimini) alabilen ParentWave.Name adlı dalgaları analiz eder. Analiz edilen dalga NumWave, dalga ağacının düğümünde, alt düğüm Düğümü'nde depolanacaktır.
Örneğin ParentWave.Name = "Dürtü", NumWave = 5, Alt Dalgalar = "Dürtü, Diyagonal ve Düzey = 2 ise NotStartedAndNotFinishedWaves işlevinin iki dalga düzeyine sahip olan Dürtünün beşinci dalgasını analiz edeceğini ve bir Dürtü veya Diyagonal biçimini alabileceğini söyleyebiliriz.
Örnek olarak, NotStartedAndNotFinishedWaves işlevindeki 1<-2-3> başlamamış ve bitmemiş dalgaların algoritma analizinin bir blok diyagramını kullanalım:
<img alt="Şekil 15. "1"" title="Şekil 15. formülü ile dalga analizinin blok diyagramı "1"" src="http://p.mql5.com/data/2/260/fig15.gif" style="vertical-align:middle;" height="1746" width="750"> formülüyle dalga analizinin blok diyagramı
Şekil 15. "1<-2-3>" formülü ile dalga analizinin blok diyagramı
NotStartedAndNotFinishedWaves işlevi kullanılırken aşağıdaki işlevler çağrılır: NotStartedWaves, NotFinishedWaves ve FinishedWaves.
Başlamamış dalgaların analizi için işlev:
void NotStartedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level)
NotStartedWaves işlevi, ilk dalga grubunun tüm dalgalarını - başlamamış dalgaları - analiz eder. İşlev, alt dalga dalgaları biçimini alabilen ParentWave.Name adlı dalganın NumWave dalgasını (dalga seviyesi Düzeyiyle birlikte) analiz eder. Analiz edilen dalga NumWave, dalga ağacının düğümünde, alt düğüm Düğümü'nde depolanacaktır.
NotStartedWaves işlevi çalışırken, aşağıdaki işlevler çağrılır: NotStartedWaves ve FinishedWaves.
Tüm dalgalar, Şekil 15'teki blok diyagramına benzer şekilde analiz edilir.
Bitmemiş dalgaların işlev analizi:
void NotFinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level)
NotFinishedWaves işlevi, ikinci dalga grubunun tüm dalgalarını - bitmemiş dalgaları - analiz eder. İşlev, alt dalga dalgaları biçimini alabilen ParentWave.Name adlı dalganın NumWave dalgasını (dalga seviyesi Düzeyi ile) analiz eder. Analiz edilen dalga NumWave, dalga ağacının düğümünde, alt düğüm Düğümü'nde depolanacaktır.
NotFinishedWaves işlevi çalışırken, aşağıdaki işlevler çağrılır: NotFinishedWaves ve FinishedWaves.
Tüm dalgalar, Şekil 15'teki blok diyagramına benzer şekilde analiz edilir.
Tamamlanmış (bitmiş) dalgaların işlev analizi:
void FinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level)
FinishedWaves işlevi, dördüncü grubun tüm dalgalarını - tamamlanmış dalgaları - analiz eder. İşlev, alt dalga dalgaları biçimini alabilen ParentWave.Name adlı dalganın NumWave dalgasını (dalga seviyesi Düzeyiyle birlikte) analiz eder. Analiz edilen dalga NumWave, dalga ağacının düğümünde, alt düğüm Düğümü'nde depolanacaktır.
FinishedWaves işlevi çalışırken, FinishedWaves işlevi çağrılır.
Tüm dalgalar, Şekil 15'teki blok diyagramına benzer şekilde analiz edilir.
5.8. FindWaveInWaveDescription
WaveDescription veri yapısında dalga arama işlevi:
int FindWaveInWaveDescription(string NameWave)
Bir parametre olarak iletilen NameWave dalgasının adına göre FindWaveInWaveDescription işlevi, WaveDescription yapı dizisinde onu arar ve bu dalgaya karşılık gelen indeks numarasını döndürür.
WaveDescription yapıları dizisi şu şekilde görünür:
TWaveDescription WaveDescription[]= { { "Impulse",5, { "", "Impulse,Leading Diagonal,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Impulse,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Impulse,Diagonal," } } , { "Leading Diagonal",5, { "", "Impulse,Leading Diagonal,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Impulse,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Impulse,Diagonal," } } , { "Diagonal",5, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle," } } , { "Zigzag",3, { "", "Impulse,Leading Diagonal,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Impulse,Diagonal,", "", "" } } , { "Flat",3, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Impulse,Diagonal,", "", "" } } , { "Double Zigzag",3, { "", "Zigzag,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,", "", "" } } , { "Triple Zigzag",5, { "", "Zigzag,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag," } } , { "Double Three",3, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "", "" } } , { "Triple Three",5, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle," } } , { "Contracting Triangle",5, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle," } } , { "Expanding Triangle",5, { "", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle,", "Zigzag,Flat,Double Zigzag,Triple Zigzag,Double Three,Triple Three,Contracting Triangle,Expanding Triangle," } } };
FindWaveInWaveDescription işlevi, aşağıdaki dalgaların işlev analizinde kullanılır: NotStartedAndNotFinishedWaves, NotStartedWaves, NotFinishedWaves ve FinishedWaves.
Grafiğin verilen bölümünün halihazırda analiz edilip edilmediğini kontrol eden işlev:
bool Already(TWave *Wave,int NumWave,TNode *Node,string Subwaves)
Elliott Dalgalarının otomatik analizi, numaralandırma yöntemiyle gerçekleştiği için, grafiğin verilen bölümü zaten bir dalga veya dalga grubunun varlığı için analiz edildiğinde bir durum ortaya çıkabilir. Bunu bilmek için, halihazırda analiz edilmiş dalganın dalgalar ağacındaki düğüme olan bağlantıyı kaydetmeniz ve ancak o zaman bağlantıyı çıkarmanız gerekir. Tüm bunlar Already işlevinde gerçekleşir.
Already işlevi, Wave adlı dalganın NumWave dalgasına karşılık gelen grafiğin aralığı olan TNodeInfo sınıfının nesnelerini depolayan genel bir NodeInfoArray dizisini arar. Alt dalga dalgaları şeklinde olan ve grafiğin önceden işaretlenmiş bölümünün düğümüne ait adresi Düğüme kaydeden ad. Bu bölüm yoksa, yeni bir TNodeInfo sınıfı nesnesi oluşturulur ve doldurulur ve NodeInfoArray dizisine kaydedilir.
Grafiğin aralığı halihazırda analiz edilmişse işlev true değerini döndürür, aksi takdirde false değerini döndürür.
NodeInfoArray dizisi şu şekilde bildirilir:
CArrayObj NodeInfoArray;
5.10. Kurallar için dalgaları kontrol etme işlevleri
İlk iki işlevin çağrıldığı VertexAAboveB, WaveAMoreWaveB ve WaveRules işlevlerini içerir. Test ederken, dalgaların başlamamış ve (veya) bitmemiş olabileceğini ve örneğin "1<-2-3>" formülüne sahip dalga için, dördüncü dalganın birinci dalganın bölgesinin ötesine geçip geçmediğinin belirlenemeyeceğini (henüz dördüncü dalga olmadığı için) unutmayın.
Kurallar için dalgaları kontrol etme işlevi:
bool WaveRules(TWave *Wave)
Wave.Name adlı dalga "doğru" ise WaveRules işlevi true değerini döndürür, aksi takdirde false değerini döndürür. Çalışmasında WaveRules işlevi, VertexAAboveVertexB ve WaveAMoreWaveB işlevi tarafından çağrılır.
Bir tepe noktasının diğer bir tepe noktası üzerindeki fazlalığını kontrol etme işlevi:
int VertexAAboveVertexB(int A,int B,bool InternalPoints)
VertexAAboveVertexB işlevi, A dalgasının tepe kısmı B dalgasının tepe kısmını aşarsa > = 0 sayısını döndürür, aksi takdirde -1 sayısını döndürür. InternalPoints = true ise, bu durumda dalgaların iç noktaları (dalgaların maksimum ve (veya)minimum değerleri) dikkate alınır.
Bir dalganın uzunluğunun diğerinin uzunluğu üzerindeki fazlalığını kontrol etme işlevi:
int WaveAMoreWaveB(int A,int B)
WaveAMoreWaveB işlevi, A dalgası B dalgasından büyükse >=0 sayısını döndürür, aksi takdirde -1 sayısını döndürür.
11. Belleği temizleme işlevi
Üst düğüm Düğümü ile dalga ağacını temizleme işlevi:
void ClearTree(TNode *Node)
İşlev, ClearNodeInfoArray dizisini temizler:
void ClearNodeInfoArray()
ZigzagArray dizisini temizleme işlevi:
void ClearZigzagArray()
5.12. Dalga ağacını atlama ve analiz sonuçlarını grafiğe gönderme işlevi
Elliott Dalgalarının otomatik analizinin tamamlanmasından sonra, bir dalga ağacımız var.
Bunun örneği aşağıdaki şekildeki gibi sunulabilir:
Şekil 16. Dalga ağacı örneği
Şimdi, analizin sonuçlarını grafikte görüntülemek için verilen ağacın etrafında gezinmemiz gerekiyor. Şekil 16'da gösterildiği gibi, oldukça fazla seçenek vardır (çünkü birkaç dalga seçeneği vardır) ve her bir atlama seçeneği farklı işaretlemelere yol açar.
İki tür ağaç düğümü ayırt edebiliriz.
İlk tür - dalga adlarına sahip düğümler ("Dürtü", "Zigzag" vb.). İkinci tür - dalga numarasına sahip düğümler ("1", "1<", "vb.). Dalganın parametreleri hakkındaki tüm bilgiler, düğümlerin ilk türünde depolanır. Bu nedenle, bu düğümleri ziyaret ederken, daha sonra grafikte görüntülemek için dalga hakkında bilgi alıp kaydedeceğiz.
Basit olması için, dalgaların yalnızca ilk sürümlerini ziyaret ederek ağacı atlayacağız.
Bir atlama örneği Şekil 17'de gösterilmiştir ve kırmızı ile vurgulanmıştır.
Şekil 17. Dalga ağacını atlama örneği
Dalga ağacını atlama işlevi:
void FillLabelArray(TNode *Node)
FillLabelArray işlevi, kök Düğüme sahip dalga ağacını atlayarak, ağaçtaki dalgaların yalnızca ilk sürümlerine katılır ve indeksleri grafikte verilen indekse sahip tepe noktalarının dizisine (TLabel sınıfının nesneler dizisi) bir bağlantı depolayan bir genel LabelArray dizisini doldurur.
LabelArray dizisi şu şekilde tanımlanır:
CArrayObj *LabelArray[];
Analiz sonuçlarını grafikte görüntüleme işlevi:
void CreateLabels()
CreateLabels işlevi, grafikteki dalga etiketlerine karşılık gelen "Metin" grafik nesnelerini oluşturur. Dalgaların etiketleri, LabelArray dizisine dayalı olarak oluşturulur.
Grafikteki dalgaların tepe kısımlarını (düzeltme) güncelleme işlevi:
void CorrectLabel()
CorrectLabel işlevi, kaydırıldığında ve (veya) kısıtlanması sırasında grafikteki dalga etiketlerini düzeltir.
6. Elliott Dalgalarının otomatik bölümlemesinin uygulanması
6.1. Zigzag işlevi:
//+------------------------------------------------------------------+ //| The Zigzag function | //+------------------------------------------------------------------+ int Zigzag(int H,int Start,int Finish,CArrayInt *IndexVertex,CArrayDouble *ValueVertex) { bool Up=true; double dH=H*Point(); int j=0; int TempMaxBar = Start; int TempMinBar = Start; double TempMax = rates[Start].high; double TempMin = rates[Start].low; for(int i=Start+1;i<=Finish;i++) { // processing the case of a rising segment if(Up==true) { // check that the current maximum has not changed if(rates[i].high>TempMax) { // if it has, correct the corresponding variables TempMax=rates[i].high; TempMaxBar=i; } else if(rates[i].low<TempMax-dH) { // otherwise, if the lagged level is broken, fixate the maximum ValueVertex.Add(TempMax); IndexVertex.Add(TempMaxBar); j++; // correct the corresponding variables Up=false; TempMin=rates[i].low; TempMinBar=i; } } else { // processing the case of the descending segment // check that the current minimum hasn't changed if(rates[i].low<TempMin) { // if it has, correct the corresponding variables TempMin=rates[i].low; TempMinBar=i; } else if(rates[i].high>TempMin+dH) { // otherwise, if the lagged level is broken, fix the minimum ValueVertex.Add(TempMin); IndexVertex.Add(TempMinBar); j++; // correct the corresponding variables Up=true; TempMax=rates[i].high; TempMaxBar=i; } } } // return the number of zigzag tops return(j); }
6.2. FillZigzagArray işlevi:
CArrayObj *ZigzagArray; // declare the ZigzagArray global dynamic array //+------------------------------------------------------------------+ //| The FillZigzagArray function | //| search through the values of the parameter H zigzag | //| and fill the array ZigzagArray | //+------------------------------------------------------------------+ void FillZigzagArray(int Start,int Finish) { ZigzagArray=new CArrayObj; // create the dynamic array of zigzags CArrayInt *IndexVertex=new CArrayInt; // create the dynamic array of indexes of zigzag tops CArrayDouble *ValueVertex=new CArrayDouble; // create the dynamic array of values of the zigzag tops TZigzag *Zigzag; // declare the class for storing the indexes and values of the zigzag tops int H=1; int j=0; int n=Zigzag(H,Start,Finish,IndexVertex,ValueVertex);//find the tops of the zigzag with the parameter H=1 if(n>0) { // store the tops of the zigzag in the array ZigzagArray Zigzag=new TZigzag; // create the object for storing the found indexes and the zigzag tops, // fill it and store in the array ZigzagArray Zigzag.IndexVertex=IndexVertex; Zigzag.ValueVertex=ValueVertex; ZigzagArray.Add(Zigzag); j++; } H++; // loop of the H of the zigzag while(true) { IndexVertex=new CArrayInt; // create a dynamic array of indexes of zigzag tops ValueVertex=new CArrayDouble; // create a dynamic array of values of the zigzag tops n=Zigzag(H,Start,Finish,IndexVertex,ValueVertex); // find the tops of the zigzag if(n>0) { Zigzag=ZigzagArray.At(j-1); CArrayInt *PrevIndexVertex=Zigzag.IndexVertex; // get the array of indexes of the previous zigzag bool b=false; // check if there is a difference between the current zigzag and the previous zigzag for(int i=0; i<=n-1;i++) { if(PrevIndexVertex.At(i)!=IndexVertex.At(i)) { // if there is a difference, store the tops of a zigzag in the array ZigzagArray Zigzag=new TZigzag; Zigzag.IndexVertex=IndexVertex; Zigzag.ValueVertex=ValueVertex; ZigzagArray.Add(Zigzag); j++; b=true; break; } } if(b==false) { // otherwise, if there is no difference, release the memory delete IndexVertex; delete ValueVertex; } } // search for the tops of the zigzag until there is two or less of them if(n<=2) break; H++; } }
6.3. FindPoints işlevi:
//+------------------------------------------------------------------+ //| The FindPoints function | //| Fill the ValuePoints and IndexPoints arrays | //| of the Points structure | //+------------------------------------------------------------------+ bool FindPoints(int NumPoints,int IndexStart,int IndexFinish,double ValueStart,double ValueFinish,TPoints &Points) { int n=0; // fill the array ZigzagArray for(int i=ZigzagArray.Total()-1; i>=0;i--) { TZigzag *Zigzag=ZigzagArray.At(i); // the obtained i zigzag in the ZigzagArray CArrayInt *IndexVertex=Zigzag.IndexVertex; // get the array of the indexes of the tops of the i zigzags CArrayDouble *ValueVertex=Zigzag.ValueVertex; // get the array of values of the tops of the i zigzag int Index1=-1,Index2=-1; // search the index of the IndexVertex array, corresponding to the first point for(int j=0;j<IndexVertex.Total();j++) { if(IndexVertex.At(j)>=IndexStart) { Index1=j; break; } } // search the index of the IndexVertex array, corresponding to the last point for(int j=IndexVertex.Total()-1;j>=0;j--) { if(IndexVertex.At(j)<=IndexFinish) { Index2=j; break; } } // if the first and last points were found if((Index1!=-1) && (Index2!=-1)) { n=Index2-Index1+1; // find out how many points were found } // if the required number of points was found (equal or greater) if(n>=NumPoints) { // check that the first and last tops correspond with the required top values if(((ValueStart!=0) && (ValueVertex.At(Index1)!=ValueStart)) || ((ValueFinish!=0) && (ValueVertex.At(Index1+n-1)!=ValueFinish)))continue; // fill the Points structure, passed as a parameter Points.NumPoints=n; ArrayResize(Points.ValuePoints, n); ArrayResize(Points.IndexPoints, n); int k=0; // fill the ValuePoints and IndexPoints arrays of Points structure for(int j=Index1; j<Index1+n;j++) { Points.ValuePoints[k]=ValueVertex.At(j); Points.IndexPoints[k]=IndexVertex.At(j); k++; } return(true); }; }; return(false); };
6.4. NotStartedAndNotFinishedWaves işlevi:
//+------------------------------------------------------------------+ //| The NotStartedAndNotFinishedWaves function | //+------------------------------------------------------------------+ void NotStartedAndNotFinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level) { int v1,v2,v3,v4,I; TPoints Points; TNode *ParentNode,*ChildNode; int IndexWave; string NameWave; TWave *Wave; int i=0,pos=0,start=0; // Put the waves, which we will be analyzing to the ListNameWave array string ListNameWave[]; ArrayResize(ListNameWave,ArrayRange(WaveDescription,0)); while(pos!=StringLen(Subwaves)-1) { pos=StringFind(Subwaves,",",start); NameWave=StringSubstr(Subwaves,start,pos-start); ListNameWave[i++]=NameWave; start=pos+1; } int IndexStart=ParentWave.IndexVertex[NumWave-1]; int IndexFinish=ParentWave.IndexVertex[NumWave]; double ValueStart = ParentWave.ValueVertex[NumWave - 1]; double ValueFinish= ParentWave.ValueVertex[NumWave]; // find no less than two points on the price chart and put them into the structure Points // if they are not found, then exit the function if(FindPoints(2,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unbegun and incomplete waves with the formula "1<-2-3>" v1=0; while(v1<=Points.NumPoints-2) { v2=v1+1; while(v2<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the structure WaveDescription in order to // find out the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if((WaveDescription[IndexWave].NumWave==5) || (WaveDescription[IndexWave].NumWave==3)) { // create the object of TWave class and fill its fields - parameters of the analyzed waves Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2-3>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = IndexFinish; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if a wave passed the check by rules, add it into the wave tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create a third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release memory else delete Wave; } } v2=v2+2; } v1=v1+2; } // the loop of unbegun and unfinished waves with the formula "2<-3-4>" v2=0; while(v2<=Points.NumPoints-2) { v3=v2+1; while(v3<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its symbols and its names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="2<-3-4>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = IndexStart; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = IndexFinish; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check for rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=2; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in th waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by rules, release memory else delete Wave; } } v3=v3+2; } v2=v2+2; } // the loop of the unbegun and the incomplete waves with the formula "3<-4-5>" v3=0; while(v3<=Points.NumPoints-2) { v4=v3+1; while(v4<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to // find out the number of its symbols and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="3<-4-5>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = 0; Wave.IndexVertex[2] = IndexStart; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = IndexFinish; // check the wave for the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=3; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave has not passed the check by the rules, release the memory else delete Wave; } } v4=v4+2; } v3=v3+2; } // find no less than three points on the price chart and put them in the Points structure // if they were not found, then exit the function if(FindPoints(3,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false) return; // the loop of unbegun and unfinished waved with the formula "1<-2-3-4>" v1=0; while(v1<=Points.NumPoints-3) { v2=v1+1; while(v2<=Points.NumPoints-2) { v3=v2+1; while(v3<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create an object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2-3-4>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = IndexFinish; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waved tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave of the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v3=v3+2; } v2=v2+2; } v1=v1+2; } // the loop of unbegun and unfinished waves with the formula "2<-3-4-5>" v2=0; while(v2<=Points.NumPoints-3) { v3=v2+1; while(v3<=Points.NumPoints-2) { v4=v3+1; while(v4<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of the symbols and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="2<-3-4-5>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = IndexStart; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = IndexFinish; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=2; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waved tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave has not passed by the rules, release the memory else delete Wave; } } v4=v4+2; } v3=v3+2; } v2=v2+2; } // find no less than four point on the price chart and put them into the structure Points // if we didn't find any, then exit the function if(FindPoints(4,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false) return; // the loop of unbegun and unfinished waves with the formula "1<-2-3-4-5>" v1=0; while(v1<=Points.NumPoints-4) { v2=v1+1; while(v2<=Points.NumPoints-3) { v3=v2+1; while(v3<=Points.NumPoints-2) { v4=v3+1; while(v4<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2-3-4-5>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = IndexFinish; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waved tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the 5th sub-wave in the wave tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by the rules, release the memory else delete Wave; } } v4=v4+2; } v3=v3+2; } v2=v2+2; } v1=v1+2; } // find no less than one point on the price chart and record it into the structure Points // if we didn't find any, then exit the function if(FindPoints(1,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unbegun and unfinished waves with the formula "1<-2>" v1=0; while(v1<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5 || WaveDescription[IndexWave].NumWave==3) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = IndexFinish; Wave.IndexVertex[3] = 0; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waved tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by the rules, release the memory else delete Wave; } } v1=v1+1; } // loop the unbegun and unfinished waves with the formula "2<-3>" v2=0; while(v2<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the structure WaveDescription, in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5 || WaveDescription[IndexWave].NumWave==3) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="2<-3>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = IndexStart; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = IndexFinish; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=2; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waved tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v2=v2+1; } // the loop of unbegun and unfinished waves with the formula "3<-4>" v3=0; while(v3<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure on order to know the number of sub-waved and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="3<-4>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = 0; Wave.IndexVertex[2] = IndexStart; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = IndexFinish; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=3; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v3=v3+1; } // the loop of unbegun and unfinished waves with the formula "4<-5>" v4=0; while(v4<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of symbols and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="4<-5>"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = 0; Wave.IndexVertex[2] = 0; Wave.IndexVertex[3] = IndexStart; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = IndexFinish; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=4; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v4=v4+1; } }
6.5. NotStartedWaves işlevi:
//+------------------------------------------------------------------+ //| The function NotStartedWaves | //+------------------------------------------------------------------+ void NotStartedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level) { int v1,v2,v3,v4,v5,I; TPoints Points; TNode *ParentNode,*ChildNode; int IndexWave; string NameWave; TWave *Wave; int i=0,Pos=0,Start=0; // Put the waves, which we will be analyzing to the ListNameWave array string ListNameWave[]; ArrayResize(ListNameWave,ArrayRange(WaveDescription,0)); while(Pos!=StringLen(Subwaves)-1) { Pos=StringFind(Subwaves,",",Start); NameWave=StringSubstr(Subwaves,Start,Pos-Start); ListNameWave[i++]=NameWave; Start=Pos+1; } int IndexStart=ParentWave.IndexVertex[NumWave-1]; int IndexFinish=ParentWave.IndexVertex[NumWave]; double ValueStart = ParentWave.ValueVertex[NumWave - 1]; double ValueFinish= ParentWave.ValueVertex[NumWave]; // find no less than two points on the price chart and put them into the structure Points // if we didn't find any, then exit the function if(FindPoints(2,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // loop the unbegun waves with the formula "4<-5" v5=Points.NumPoints-1; v4=v5-1; while(v4>=0) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="4<-5"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = Points.ValuePoints[v5]; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = 0; Wave.IndexVertex[2] = 0; Wave.IndexVertex[3] = IndexStart; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = Points.IndexPoints[v5]; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=4; // create the fourth sub-wave in the wave tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create 5th sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by the rules, release the memory else delete Wave; } } v4=v4-2; } // loop the unbegun waves with the formula "2<-3" v3=Points.NumPoints-1; v2=v3-1; while(v2>=0) { int j=0; while(j<=i-1) { // in turn, from the ListNameWave, draw the name of the wave for analysis NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==3) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="2<-3"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = IndexStart; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=2; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v2=v2-2; } // find not less than three points on the price chart and put them into the structure Points // if we didn't find any, then exit the function if(FindPoints(3,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // loop the unbegun waves with the formula "3<-4-5" v5=Points.NumPoints-1; v4=v5-1; while(v4>=1) { v3=v4-1; while(v3>=0) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="3<-4-5"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = Points.ValuePoints[v5]; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = 0; Wave.IndexVertex[2] = IndexStart; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = Points.IndexPoints[v5]; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=3; // create the three sub-waves in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v3=v3-2; } v4=v4-2; } // the loop of the unbegun waves with the formula "1<-2-3" v3=Points.NumPoints-1; v2=v3-1; while(v2>=1) { v1=v2-1; while(v1>=0) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==3) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2-3"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); //if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); //if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v1=v1-2; } v2=v2-2; } // find no less than four points on the price chart and put them into the structure Points // if we didn't find any, then exit the function if(FindPoints(4,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unbegun waves with the formula "2<-3-4-5" v5=Points.NumPoints-1; v4=v5-1; while(v4>=2) { v3=v4-1; while(v3>=1) { v2=v3-1; while(v2>=0) { int j=0; while(j<=i-1) { // in turn, from the ListNameWave, draw the name of the wave for analysis NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="2<-3-4-5"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = Points.ValuePoints[v5]; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = IndexStart; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = Points.IndexPoints[v5]; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=2; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave has not passed the rules, release the memory else delete Wave; } } v2=v2-2; } v3=v3-2; } v4=v4-2; } // find no less than five points on the price chart and record it into the structure Points // if we didn't find any, then exit the function if(FindPoints(5,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unbegun waves with the formula "1<-2-3-4-5" v5=Points.NumPoints-1; v4=v5-1; while(v4>=3) { v3=v4-1; while(v3>=2) { v2=v3-1; while(v2>=1) { v1=v2-1; while(v1>=0) { int j=0; while(j<=i-1) { // in turn, from the ListNameWave, draw the name of the wave for analysis NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1<-2-3-4-5"; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = Points.ValuePoints[v5]; Wave.IndexVertex[0] = IndexStart; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = Points.IndexPoints[v5]; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotStartedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the chart, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v1=v1-2; } v2=v2-2; } v3=v3-2; } v4=v4-2; } }
6.6. NotFinishedWaves işlevi:
//+------------------------------------------------------------------+ //| The function FinishedWaves | //+------------------------------------------------------------------+ void NotFinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level) { int v0,v1,v2,v3,v4,I; TPoints Points; TNode *ParentNode,*ChildNode; int IndexWave; string NameWave; TWave *Wave; int i=0,Pos=0,Start=0; //we put the waves, which we will be analyzing in the array ListNameWaveg string ListNameWave[]; ArrayResize(ListNameWave,ArrayRange(WaveDescription,0)); while(Pos!=StringLen(Subwaves)-1) { Pos=StringFind(Subwaves,",",Start); NameWave=StringSubstr(Subwaves,Start,Pos-Start); ListNameWave[i++]=NameWave; Start=Pos+1; } int IndexStart=ParentWave.IndexVertex[NumWave-1]; int IndexFinish=ParentWave.IndexVertex[NumWave]; double ValueStart = ParentWave.ValueVertex[NumWave - 1]; double ValueFinish= ParentWave.ValueVertex[NumWave]; // find not less than two points on the price chart and record it into the structure Points // if we didn't find any, then exit the function if(FindPoints(2,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unfinished waves with the formula "1-2>" v0=0; v1=v0+1; while(v1<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from the ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if((WaveDescription[IndexWave].NumWave==5) || (WaveDescription[IndexWave].NumWave==3)) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1-2>"; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = 0; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = IndexFinish; Wave.IndexVertex[3] = 0; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v1=v1+2; } // find no less than three points on the price chart and put it into the Points structure // if none were found, then exit the function if(FindPoints(3,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unfinished waves with the formula "1-2-3>" v0=0; v1=v0+1; while(v1<=Points.NumPoints-2) { v2=v1+1; while(v2<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if((WaveDescription[IndexWave].NumWave==5) || (WaveDescription[IndexWave].NumWave==3)) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1-2-3>"; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = 0; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = IndexFinish; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, of the corresponding third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v2=v2+2; } v1=v1+2; } // find no less than four points on the price chart and record it into the Points structure // if none were found, then exit the function if(FindPoints(4,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false) return; // the loop of unfinished waves with the formula "1-2-3-4>" v0=0; v1=v0+1; while(v1<=Points.NumPoints-3) { v2=v1+1; while(v2<=Points.NumPoints-2) { v3=v2+1; while(v3<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in WaveDescription structure in order to know the number of sub-waves and the names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1-2-3-4>"; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = IndexFinish; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check for the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave didn't pass by the rules, release the memory else delete Wave; } } v3=v3+2; } v2=v2+2; } v1=v1+2; } // find no less than five points on the price chart and put them into the structure Points // if none were found, exit the function if(FindPoints(5,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of unfinished waves with the formula "1-2-3-4-5>" v0=0; v1=v0+1; while(v1<=Points.NumPoints-4) { v2=v1+1; while(v2<=Points.NumPoints-3) { v3=v2+1; while(v3<=Points.NumPoints-2) { v4=v3+1; while(v4<=Points.NumPoints-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of TWave class and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1-2-3-4-5>"; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = IndexFinish; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) NotFinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass by the rules, release the memory else delete Wave; } } v4=v4+2; } v3=v3+2; } v2=v2+2; } v1=v1+2; } }
6.7. FinishedWaves işlevi:
//+------------------------------------------------------------------+ //| The FinishedWaves function | //+------------------------------------------------------------------+ void FinishedWaves(TWave *ParentWave,int NumWave,TNode *Node,string Subwaves,int Level) { int v0,v1,v2,v3,v4,v5,I; TPoints Points; TNode *ParentNode,*ChildNode; int IndexWave; string NameWave; TWave *Wave; int i=0,Pos=0,Start=0; // Put the waves, which we will be analyzing to the ListNameWave array string ListNameWave[]; ArrayResize(ListNameWave,ArrayRange(WaveDescription,0)); while(Pos!=StringLen(Subwaves)-1) { Pos=StringFind(Subwaves,",",Start); NameWave=StringSubstr(Subwaves,Start,Pos-Start); ListNameWave[i++]=NameWave; Start=Pos+1; } int IndexStart=ParentWave.IndexVertex[NumWave-1]; int IndexFinish=ParentWave.IndexVertex[NumWave]; double ValueStart = ParentWave.ValueVertex[NumWave - 1]; double ValueFinish= ParentWave.ValueVertex[NumWave]; // find no less than four points on the price chart and put them into the structure Points // if none were found, then exit the function if(FindPoints(4,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false) return; // the loop of complete waves with the formula "1-2-3" v0 = 0; v1 = 1; v3 = Points.NumPoints - 1; while(v1<=v3-2) { v2=v1+1; while(v2<=v3-1) { int j=0; while(j<=i-1) { // in tuen, from ListNameWave, draw the name of the wave for analysis NameWave=ListNameWave[j++]; // find the index of the wave in the structure WaveDescription in order to know the number of sub-waves and its names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==3) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave;; Wave.Name=NameWave; Wave.Formula="1-2-3"; Wave.Level=Level; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = 0; Wave.ValueVertex[5] = 0; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = 0; Wave.IndexVertex[5] = 0; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(i)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(i)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by the rules, release the memory else delete Wave; } } v2=v2+2; } v1=v1+2; } // find no less than six points on the price chart and put them into the structure Points // if none were found, then exit the function if(FindPoints(6,IndexStart,IndexFinish,ValueStart,ValueFinish,Points)==false)return; // the loop of complete waves with the formula "1-2-3-4-5" v0 = 0; v1 = 1; v5 = Points.NumPoints - 1; while(v1<=v5-4) { v2=v1+1; while(v2<=v5-3) { v3=v2+1; while(v3<=v5-2) { v4=v3+1; while(v4<=v5-1) { int j=0; while(j<=i-1) { // get the name of the wave for analysis from ListNameWave NameWave=ListNameWave[j++]; // find the index of the wave in the WaveDescription structure in order to know the number of its sub-waves and their names IndexWave=FindWaveInWaveDescription(NameWave); if(WaveDescription[IndexWave].NumWave==5) { // create the object of class TWave and fill its fields - parameters of the analyzed wave Wave=new TWave; Wave.Name=NameWave; Wave.Level=Level; Wave.Formula="1-2-3-4-5"; Wave.ValueVertex[0] = Points.ValuePoints[v0]; Wave.ValueVertex[1] = Points.ValuePoints[v1]; Wave.ValueVertex[2] = Points.ValuePoints[v2]; Wave.ValueVertex[3] = Points.ValuePoints[v3]; Wave.ValueVertex[4] = Points.ValuePoints[v4]; Wave.ValueVertex[5] = Points.ValuePoints[v5]; Wave.IndexVertex[0] = Points.IndexPoints[v0]; Wave.IndexVertex[1] = Points.IndexPoints[v1]; Wave.IndexVertex[2] = Points.IndexPoints[v2]; Wave.IndexVertex[3] = Points.IndexPoints[v3]; Wave.IndexVertex[4] = Points.IndexPoints[v4]; Wave.IndexVertex[5] = Points.IndexPoints[v5]; // check the wave by the rules if(WaveRules(Wave)==true) { // if the wave passed the check by the rules, add it to the waves tree ParentNode=Node.Add(NameWave,Wave); I=1; // create the first sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the first sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the second sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the second sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the third sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the third sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fourth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fourth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); I++; // create the fifth sub-wave in the waves tree ChildNode=ParentNode.Add(IntegerToString(I)); // if the interval of the chart, corresponding to the fifth sub-wave, has not been analyzed, then analyze it if(Already(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I])==false) FinishedWaves(Wave,I,ChildNode,WaveDescription[IndexWave].Subwaves[I],Level+1); } // otherwise, if the wave did not pass the check by the rules, release the memory else delete Wave; } } v4=v4+2; } v3=v3+2; } v2=v2+2; } v1=v1+2; } }
6.8. FindWaveInWaveDescription işlevi:
//+------------------------------------------------------------------+ //| The FindWaveInWaveDescription function | //+------------------------------------------------------------------+ int FindWaveInWaveDescription(string NameWave) { for(int i=0;i<ArrayRange(WaveDescription,0);i++) if(WaveDescription[i].NameWave==NameWave)return(i); return(-1); }
6.9. Already işlevi:
//+------------------------------------------------------------------+ //| The Already function | //+------------------------------------------------------------------+ bool Already(TWave *Wave,int NumWave,TNode *Node,string Subwaves) { // obtain the necessary parameters of the wave or the group of waves int IndexStart=Wave.IndexVertex[NumWave-1]; int IndexFinish=Wave.IndexVertex[NumWave]; double ValueStart = Wave.ValueVertex[NumWave - 1]; double ValueFinish= Wave.ValueVertex[NumWave]; // in the loop, proceed the array NodeInfoArray for the search of the marked-up section of the chart for(int i=NodeInfoArray.Total()-1; i>=0;i--) { TNodeInfo *NodeInfo=NodeInfoArray.At(i); // if the required section has already been marked-up if(NodeInfo.Subwaves==Subwaves && (NodeInfo.ValueStart==ValueStart) && (NodeInfo.ValueFinish==ValueFinish) && (NodeInfo.IndexStart==IndexStart) && (NodeInfo.IndexFinish==IndexFinish)) { // add the child nodes of the found node into the child nodes of the new node for(int j=0;j<NodeInfo.Node.Child.Total();j++) Node.Child.Add(NodeInfo.Node.Child.At(j)); return(true); // exit the function } } // if the interval has not been marked-up earlier, then record its data into the array NodeInfoArray TNodeInfo *NodeInfo=new TNodeInfo; NodeInfo.IndexStart=IndexStart; NodeInfo.IndexFinish=IndexFinish; NodeInfo.ValueStart=ValueStart; NodeInfo.ValueFinish=ValueFinish; NodeInfo.Subwaves=Subwaves; NodeInfo.Node=Node; NodeInfoArray.Add(NodeInfo); return(false); }
6.10. WaveRules işlevi:
int IndexVertex[6]; // the indexes of the tops of the wave double ValueVertex[6],Maximum[6],Minimum[6]; // the balues of the tops of the wave, as well as the maximum and minimum values of the wave string Trend; // direction of the trend - "Up" or "Down" string Formula; // the formula of the wave - "1<2-3>" or "1-2-3>" etc. int FixedVertex[6]; // information about the tops of the wave, whether or not they have been fixed //+------------------------------------------------------------------+ //| The function WaveRules | //+------------------------------------------------------------------+ bool WaveRules(TWave *Wave) { Formula=Wave.Formula; bool Result=false; // fill the array IndexVertex and ValueVertex - indexes of the tops and values of the tops of the wave for(int i=0;i<=5;i++) { IndexVertex[i]=Wave.IndexVertex[i]; ValueVertex[i]=Wave.ValueVertex[i]; FixedVertex[i]=-1; } // fill the array FixedVertex, the balues of which indicate whether or not the top of the wave is fixed int Pos1=StringFind(Formula,"<"); string Str; if(Pos1>0) { Str=ShortToString(StringGetCharacter(Formula,Pos1-1)); FixedVertex[StringToInteger(Str)]=1; FixedVertex[StringToInteger(Str)-1]=0; Pos1=StringToInteger(Str)+1; } else Pos1=0; int Pos2=StringFind(Formula,">"); if(Pos2>0) { Str=ShortToString(StringGetCharacter(Formula,Pos2-1)); FixedVertex[StringToInteger(Str)]=0; Pos2=StringToInteger(Str)-1; } else { Pos2=StringLen(Formula); Str=ShortToString(StringGetCharacter(Formula,Pos2-1)); Pos2=StringToInteger(Str); } for(int i=Pos1;i<=Pos2;i++) FixedVertex[i]=1; double High[],Low[]; ArrayResize(High,ArrayRange(rates,0)); ArrayResize(Low,ArrayRange(rates,0)); // find the maximums and minimums of the waves for(int i=1; i<=5; i++) { Maximum[i]=rates[IndexVertex[i]].high; Minimum[i]=rates[IndexVertex[i-1]].low; for(int j=IndexVertex[i-1];j<=IndexVertex[i];j++) { if(rates[j].high>Maximum[i])Maximum[i]=rates[j].high; if(rates[j].low<Minimum[i])Minimum[i]=rates[j].low; } } // find out the trend if((FixedVertex[0]==1 && ValueVertex[0]==rates[IndexVertex[0]].low) || (FixedVertex[1]==1 && ValueVertex[1]==rates[IndexVertex[1]].high) || (FixedVertex[2]==1 && ValueVertex[2]==rates[IndexVertex[2]].low) || (FixedVertex[3]==1 && ValueVertex[3]==rates[IndexVertex[3]].high) || (FixedVertex[4]==1 && ValueVertex[4]==rates[IndexVertex[4]].low) || (FixedVertex[5]==1 && ValueVertex[5]==rates[IndexVertex[5]].high)) Trend="Up"; else Trend="Down"; // check the required wave by the rules if(Wave.Name=="Impulse") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0 && VertexAAboveVertexB(4,1,true)>=0 && VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,true)>=0 && (WaveAMoreWaveB(3,1)>=0 || WaveAMoreWaveB(3,5)>=0)) Result=true; } else if(Wave.Name=="Leading Diagonal") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0 && VertexAAboveVertexB(4,2,true)>=0 && VertexAAboveVertexB(1,4,false)>=0 && VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,true)>=0&& (WaveAMoreWaveB(3,1)>=0 || WaveAMoreWaveB(3,5)>=0)) Result=true; } else if(Wave.Name=="Diagonal") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0 && VertexAAboveVertexB(4,2,true)>=0 && VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,true)>=0&& (WaveAMoreWaveB(3,1)>=0 || WaveAMoreWaveB(3,5)>=0)) Result=true; } else if(Wave.Name=="Zigzag") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0) Result=true; } else if(Wave.Name=="Flat") { if(VertexAAboveVertexB(1,0,false)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0) Result=true; } else if(Wave.Name=="Double Zigzag") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0) Result=true; } else if(Wave.Name=="Double Three") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,false)>=0) Result=true; } else if(Wave.Name=="Triple Zigzag") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(2,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,true)>=0 && VertexAAboveVertexB(3,1,false)>=0 && VertexAAboveVertexB(5,3,false) && VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,true)>=0) Result=true; } else if(Wave.Name=="Triple Three") { if(VertexAAboveVertexB(1,0,true)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,false)>=0 && VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,false)>=0) Result=true; } else if(Wave.Name=="Contracting Triangle") { if(VertexAAboveVertexB(1,0,false)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,false)>= 0&& VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,false)>=0 && WaveAMoreWaveB(2,3)>=0 && WaveAMoreWaveB(3,4)>=0 && WaveAMoreWaveB(4,5)>=0) Result=true; } else if(Wave.Name=="Expanding Triangle") { if(VertexAAboveVertexB(1,0,false)>=0 && VertexAAboveVertexB(1,2,false)>=0 && VertexAAboveVertexB(3,2,false)>= 0&& VertexAAboveVertexB(3,4,false)>=0 && VertexAAboveVertexB(5,4,false)>=0 && WaveAMoreWaveB(3,2)>=0 && WaveAMoreWaveB(3,2)>=0) Result=true; } return(Result); }
6.11. VertexAAboveVertexB işlevi:
//+-------------------------------------------------------------------------------------+ //| The function VertexAAboveVertexB checks whether or not the top A is higher than top B, | //| transferred as the parameters of the given function | //| this check can be performed only if the tops A and B - are fixed, | //| or the top A - is not fixed and prime, while the top B - is fixed, | //| or the top A - is fixed, while the top B - is not fixed and odd, | //| or the top A - is not fixed and prime, and the top B - is not fixed and odd | //+-------------------------------------------------------------------------------------+ int VertexAAboveVertexB(int A,int B,bool InternalPoints) { double VA=0,VB=0,VC=0; int IA=0,IB=0; int Result=0; if(A>=B) { IA = A; IB = B; } else if(A<B) { IA = B; IB = A; } // if the internal points of the wave must be taken into consideration if(InternalPoints==true) { if((Trend=="Up") && ((IA%2==0) || ((IA-IB==1) && (IB%2==0)))) { VA=Minimum[IA]; IA=IA-IA%2; } else if((Trend=="Down") && ((IA%2==0) || ((IA-IB==1) && (IB%2==0)))) { VA=Maximum[IA]; IA=IA-IA%2; } else if((Trend=="Up") && ((IA%2==1) || ((IA-IB==1) && (IB%2==1)))) { VA=Maximum[IA]; IA=IA -(1-IA%2); } else if((Trend=="Down") && (IA%2==1) || ((IA-IB==1) && (IB%2==1))) { VA=Minimum[IA]; IA=IA -(1-IA%2); } VB=ValueVertex[IB]; } else { VA = ValueVertex[IA]; VB = ValueVertex[IB]; } if(A>B) { A = IA; B = IB; } else if(A<B) { A = IB; B = IA; VC = VA; VA = VB; VB = VC; } if(((FixedVertex[A]==1) && (FixedVertex[B]==1)) || ((FixedVertex[A] == 0) &&(A % 2 == 0) && (FixedVertex[B] == 1)) || ((FixedVertex[A] == 1) && (FixedVertex[B] == 0) && (B %2 == 1)) || ((FixedVertex[A] == 0) & (A %2 == 0) && (FixedVertex[B] == 0) && (B % 2== 1))) { if(((Trend=="Up") && (VA>=VB)) || ((Trend=="Down") && (VA<=VB))) Result=1; else Result=-1; } return(Result); }
6.12. WaveAMoreWaveB işlevi:
//+-----------------------------------------------------------------------+ //| The function WaveAMoreWaveB checks whether or not the wave A is larger than the wave B, | //| transferred as the parameters of the given function | //| this check can be performed only if wave A - is complete, | //| and wave B - is incomplete or incomplete and unbegun | //+-----------------------------------------------------------------------+ int WaveAMoreWaveB(int A,int B) { int Result=0; double LengthWaveA=0,LengthWaveB=0; if(FixedVertex[A]==1 && FixedVertex[A-1]==1 && (FixedVertex[B]==1 || FixedVertex[B-1]==1)) { LengthWaveA=MathAbs(ValueVertex[A]-ValueVertex[A-1]); if(FixedVertex[B]==1 && FixedVertex[B-1]==1) LengthWaveB=MathAbs(ValueVertex[B]-ValueVertex[B-1]); else if(FixedVertex[B]==1 && FixedVertex[B-1]==0) { if(Trend=="Up") LengthWaveB=MathAbs(ValueVertex[B]-Minimum[B]); else LengthWaveB=MathAbs(ValueVertex[B]-Maximum[B]); } else if(FixedVertex[B]==0 && FixedVertex[B-1]==1) { if(Trend=="Up")LengthWaveB=MathAbs(ValueVertex[B-1]-Minimum[B-1]); else LengthWaveB=MathAbs(ValueVertex[B-1]-Maximum[B-1]); } if(LengthWaveA>LengthWaveB) Result=1; else Result=-1; } return(Result); }
6.13. ClearTree işlevi:
//+------------------------------------------------------------------+ //| The function of clearing the waves tree with the top node Node | //+------------------------------------------------------------------+ void ClearTree(TNode *Node) { if(CheckPointer(Node)!=POINTER_INVALID) { for(int i=0; i<Node.Child.Total();i++) ClearTree(Node.Child.At(i)); delete Node.Child; if(CheckPointer(Node.Wave)!=POINTER_INVALID)delete Node.Wave; delete Node; } }
6.14. ClearNodeInfoArray işlevi:
//+------------------------------------------------------------------+ //| The function of clearing the NodeInfoArray array | //+------------------------------------------------------------------+ void ClearNodeInfoArray() { for(int i=NodeInfoArray.Total()-1; i>=0;i--) { TNodeInfo *NodeInfo=NodeInfoArray.At(i); if(CheckPointer(NodeInfo.Node)!=POINTER_INVALID)delete NodeInfo.Node; delete NodeInfo; } NodeInfoArray.Clear(); }
6.15. ClearZigzagArray işlevi:
//+------------------------------------------------------------------+ //| The function of clearing the ZigzagArray array | //+------------------------------------------------------------------+ void ClearZigzagArray() { for(int i=0;i<ZigzagArray.Total();i++) { TZigzag *Zigzag=ZigzagArray.At(i); delete Zigzag.IndexVertex; delete Zigzag.ValueVertex; delete Zigzag; } ZigzagArray.Clear(); }
6.16. FillLabelArray işlevi:
CArrayObj *LabelArray[]; int LevelMax=0; //+------------------------------------------------------------------+ //| The FillLabelArray function | //+------------------------------------------------------------------+ void FillLabelArray(TNode *Node) { if(Node.Child.Total()>0) { // obtain the first node TNode *ChildNode=Node.Child.At(0); // obtain the structure, in which the information about the wave is stored TWave *Wave=ChildNode.Wave; string Text; // if there is a first top if(Wave.ValueVertex[1]>0) { // mark the top according to the wave if(Wave.Name=="Impulse" || Wave.Name=="Leading Diagonal" || Wave.Name=="Diagonal") Text="1"; else if(Wave.Name=="Zigzag" || Wave.Name=="Flat" || Wave.Name=="Expanding Triangle" || Wave.Name=="Contracting Triangle") Text="A"; else if(Wave.Name=="Double Zigzag" || Wave.Name=="Double Three" || Wave.Name=="Triple Zigzag" || Wave.Name=="Triple Three") Text="W"; // obtain the array of the ArrayObj tops, which have the index Wave.IndexVertex[1] on the price chart CArrayObj *ArrayObj=LabelArray[Wave.IndexVertex[1]]; if(CheckPointer(ArrayObj)==POINTER_INVALID) { ArrayObj=new CArrayObj; LabelArray[Wave.IndexVertex[1]]=ArrayObj; } // put the information about the top with the index Wave.IndexVertex[1] into the array ArrayObj TLabel *Label=new TLabel; Label.Text=Text; Label.Level=Wave.Level; if(Wave.Level>LevelMax)LevelMax=Wave.Level; Label.Value=Wave.ValueVertex[1]; ArrayObj.Add(Label); } if(Wave.ValueVertex[2]>0) { if(Wave.Name=="Impulse" || Wave.Name=="Leading Diagonal" || Wave.Name=="Diagonal") Text="2"; else if(Wave.Name=="Zigzag" || Wave.Name=="Flat" || Wave.Name=="Expanding Triangle" || Wave.Name=="Contracting Triangle") Text="B"; else if(Wave.Name=="Double Zigzag" || Wave.Name=="Double Three" || Wave.Name=="Triple Zigzag" || Wave.Name=="Triple Three") Text="X"; CArrayObj *ArrayObj=LabelArray[Wave.IndexVertex[2]]; if(CheckPointer(ArrayObj)==POINTER_INVALID) { ArrayObj=new CArrayObj; LabelArray[Wave.IndexVertex[2]]=ArrayObj; } TLabel *Label=new TLabel; Label.Text=Text; Label.Level=Wave.Level; if(Wave.Level>LevelMax)LevelMax=Wave.Level; Label.Value=Wave.ValueVertex[2]; ArrayObj.Add(Label); } if(Wave.ValueVertex[3]>0) { if(Wave.Name=="Impulse" || Wave.Name=="Leading Diagonal" || Wave.Name=="Diagonal") Text="3"; else if(Wave.Name=="Zigzag" || Wave.Name=="Flat" || Wave.Name=="Expanding Triangle" || Wave.Name=="Contracting Triangle") Text="C"; else if(Wave.Name=="Double Zigzag" || Wave.Name=="Double Three" || Wave.Name=="Triple Zigzag" || Wave.Name=="Triple Three") Text="Y"; CArrayObj *ArrayObj=LabelArray[Wave.IndexVertex[3]]; if(CheckPointer(ArrayObj)==POINTER_INVALID) { ArrayObj=new CArrayObj; LabelArray[Wave.IndexVertex[3]]=ArrayObj; } TLabel *Label=new TLabel; Label.Text=Text; Label.Level=Wave.Level; if(Wave.Level>LevelMax)LevelMax=Wave.Level; Label.Value=Wave.ValueVertex[3]; ArrayObj.Add(Label); } if(Wave.ValueVertex[4]>0) { if(Wave.Name=="Impulse" || Wave.Name=="Leading Diagonal" || Wave.Name=="Diagonal") Text="4"; else if(Wave.Name=="Expanding Triangle" || Wave.Name=="Contracting Triangle") Text="D"; else if(Wave.Name=="Triple zigzag" || Wave.Name=="Triple Three") Text="XX"; CArrayObj *ArrayObj=LabelArray[Wave.IndexVertex[4]]; if(CheckPointer(ArrayObj)==POINTER_INVALID) { ArrayObj=new CArrayObj; LabelArray[Wave.IndexVertex[4]]=ArrayObj; } TLabel *Label=new TLabel; Label.Text=Text; Label.Level=Wave.Level; if(Wave.Level>LevelMax)LevelMax=Wave.Level; Label.Value=Wave.ValueVertex[4]; ArrayObj.Add(Label); } if(Wave.ValueVertex[5]>0) { if(Wave.Name=="Impulse" || Wave.Name=="Leading Diagonal" || Wave.Name=="Diagonal") Text="5"; else if(Wave.Name=="Expanding Triangle" || Wave.Name=="Contracting Triangle") Text="E"; else if(Wave.Name=="Triple Zigzag" || Wave.Name=="Triple Three") Text="Z"; CArrayObj *ArrayObj=LabelArray[Wave.IndexVertex[5]]; if(CheckPointer(ArrayObj)==POINTER_INVALID) { ArrayObj=new CArrayObj; LabelArray[Wave.IndexVertex[5]]=ArrayObj; } TLabel *Label=new TLabel; Label.Text=Text; Label.Level=Wave.Level; if(Wave.Level>LevelMax)LevelMax=Wave.Level; Label.Value=Wave.ValueVertex[5]; ArrayObj.Add(Label); } // proceed the child nodes of the current node for(int j=0;j<ChildNode.Child.Total();j++) FillLabelArray(ChildNode.Child.At(j)); } }
6.17. CreateLabels işlevi:
double PriceInPixels; CArrayObj ObjTextArray; // declare the array, which will store the graphical objects of "Text" type //+------------------------------------------------------------------+ //| The function CreateLabels | //+------------------------------------------------------------------+ void CreateLabels() { double PriceMax =ChartGetDouble(0,CHART_PRICE_MAX,0); double PriceMin = ChartGetDouble(0,CHART_PRICE_MIN); int WindowHeight=ChartGetInteger(0,CHART_HEIGHT_IN_PIXELS); PriceInPixels=(PriceMax-PriceMin)/WindowHeight; int n=0; // loop the LabelArray array for(int i=0;i<ArrayRange(LabelArray,0);i++) { // if there are tops with the same index i if(CheckPointer(LabelArray[i])!=POINTER_INVALID) { // obtain the tops with the same indexes i CArrayObj *ArrayObj=LabelArray[i]; // loop the tops and display them on the chart for(int j=ArrayObj.Total()-1;j>=0;j--) { TLabel *Label=ArrayObj.At(j); int Level=LevelMax-Label.Level; string Text=Label.Text; double Value=Label.Value; color Color; int Size=8; if((Level/3)%2==0) { if(Text=="1") Text="i"; else if(Text == "2") Text = "ii"; else if(Text == "3") Text = "iii"; else if(Text == "4") Text = "iv"; else if(Text == "5") Text = "v"; else if(Text == "A") Text = "a"; else if(Text == "B") Text = "b"; else if(Text == "C") Text = "c"; else if(Text == "D") Text = "d"; else if(Text == "E") Text = "e"; else if(Text == "W") Text = "w"; else if(Text=="X") Text="x"; else if(Text == "XX") Text = "xx"; else if(Text == "Y") Text = "y"; else if(Text == "Z") Text = "z"; } if(Level%3==2) { Color=Green; Text="["+Text+"]"; } if(Level%3==1) { Color=Blue; Text="("+Text+")"; } if(Level%3==0) Color=Red; int Anchor; if(Value==rates[i].high) { for(int k=ArrayObj.Total()-j-1;k>=0;k--) Value=Value+15*PriceInPixels; Anchor=ANCHOR_UPPER; } else if(Value==rates[i].low) { for(int k=ArrayObj.Total()-j-1;k>=0;k--) Value=Value-15*PriceInPixels; Anchor=ANCHOR_LOWER; } CChartObjectText *ObjText=new CChartObjectText; ObjText.Create(0,"wave"+IntegerToString(n),0,rates[i].time,Value); ObjText.Description(Text); ObjText.Color(Color); ObjText.SetInteger(OBJPROP_ANCHOR,Anchor); ObjText.FontSize(8); ObjText.Selectable(true); ObjTextArray.Add(ObjText); n++; } } } ChartRedraw(); }
6.18. CorrectLabel işlevi:
//+------------------------------------------------------------------+ //| The CorrectLabel function | //+------------------------------------------------------------------+ void CorrectLabel() { double PriceMax=ChartGetDouble(0,CHART_PRICE_MAX,0); double PriceMin = ChartGetDouble(0,CHART_PRICE_MIN); int WindowHeight=ChartGetInteger(0,CHART_HEIGHT_IN_PIXELS); double CurrentPriceInPixels=(PriceMax-PriceMin)/WindowHeight; // loop all of the text objects (wave tops) and change their price size for(int i=0;i<ObjTextArray.Total();i++) { CChartObjectText *ObjText=ObjTextArray.At(i); double PriceValue=ObjText.Price(0); datetime PriceTime=ObjText.Time(0); int j; for(j=0;j<ArrayRange(rates,0);j++) { if(rates[j].time==PriceTime) break; } double OffsetInPixels; if(rates[j].low>=PriceValue) { OffsetInPixels=(rates[j].low-PriceValue)/PriceInPixels; ObjText.Price(0,rates[j].low-OffsetInPixels*CurrentPriceInPixels); } else if(rates[j].high<=PriceValue) { OffsetInPixels=(PriceValue-rates[j].high)/PriceInPixels; ObjText.Price(0,rates[j].high+OffsetInPixels*CurrentPriceInPixels); } } PriceInPixels=CurrentPriceInPixels; }
7. Başlatma, sağlamayı kaldırma ve olay işleme işlevi
OnInit işlevinde, otomatik Elliott Dalga analizörünün kontrol düğmeleri oluşturulur.
Aşağıdaki düğmeler oluşturulur:
- "Analiz Başlat" - Dalgaların otomatik analizi gerçekleşir.
- "Sonuçları göster" - Grafikte dalga işaretlerinin görüntülenmesi gerçekleşir.
- "Grafiği temizle" - Belleğin temizlenmesi ve grafikten dalga işaretlerinin silinmesi gerçekleşir.
- "İşaretleri düzelt" - Grafikteki dalgaların işaretlerini düzeltir.
Bu düğmelere basma işlemi, OnChartEvent olay işleme işlevinde gerçekleşir.
OnDeinit işlevinde, kontrol düğmeleri de dahil olmak üzere tüm grafik nesneleri grafikten kaldırılır.
#include <Object.mqh> #include <Arrays\List.mqh> #include <Arrays\ArrayObj.mqh> #include <Arrays\ArrayInt.mqh> #include <Arrays\ArrayDouble.mqh> #include <Arrays\ArrayString.mqh> #include <ChartObjects\ChartObjectsTxtControls.mqh> #include <Elliott wave\Data structures.mqh> #include <Elliott wave\Analysis functions.mqh> #include <Elliott wave\Rules functions.mqh> CChartObjectButton *ButtonStart,*ButtonShow,*ButtonClear,*ButtonCorrect; int State; //+------------------------------------------------------------------+ //| Expert initialization function | //+------------------------------------------------------------------+ int OnInit() { State=0; // create control buttons ButtonStart=new CChartObjectButton; ButtonStart.Create(0,"Begin analysis",0,0,0,150,20); ButtonStart.Description("Begin analysis"); ButtonShow=new CChartObjectButton; ButtonShow.Create(0,"Show results",0,150,0,150,20); ButtonShow.Description("Show results"); ButtonClear=new CChartObjectButton; ButtonClear.Create(0,"Clear chart",0,300,0,150,20); ButtonClear.Description("Clear chart"); ButtonCorrect=new CChartObjectButton; ButtonCorrect.Create(0,"Correct the marks",0,450,0,150,20); ButtonCorrect.Description("Correct the marks"); ChartRedraw(); return(0); } //+------------------------------------------------------------------+ //| Expert deinitialization function | //+------------------------------------------------------------------+ void OnDeinit(const int reason) { //clear waves tree ClearTree(FirstNode); //clear NodeInfoArray ClearNodeInfoArray(); //clear ZigzagArray ClearZigzagArray(); //clear LabelArray for(int i=0;i<ArrayRange(LabelArray,0);i++) { CArrayObj *ArrayObj=LabelArray[i]; if(CheckPointer(ArrayObj)!=POINTER_INVALID) { for(int j=0;j<ArrayObj.Total();j++) { TLabel *Label=ArrayObj.At(j); delete Label; } ArrayObj.Clear(); delete ArrayObj; } } //delete all of the graphical elements from the chart for(int i=ObjTextArray.Total()-1;i>=0;i--) { CChartObjectText *ObjText=ObjTextArray.At(i); delete ObjText; } ObjTextArray.Clear(); delete ButtonStart; delete ButtonShow; delete ButtonClear; delete ButtonCorrect; ChartRedraw(); } MqlRates rates[]; TNode *FirstNode; //+------------------------------------------------------------------+ //| ChartEvent function | //+------------------------------------------------------------------+ void OnChartEvent(const int id, const long &lparam, const double &dparam, const string &sparam) { if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Begin analysis" && State!=0) MessageBox("First press the button \"Clear char\""); if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Show results" && State!=1) MessageBox("First press the button \"Begin analysis\""); if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Clear chart" && State!=2) MessageBox("First press the button \"Show results\""); if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Correct the mark" && State!=2) MessageBox("First press the button \"Show results\""); //if the "Begin analysis" is pressed if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Begin analysis" && State==0) { //fill the rates array CopyRates(NULL,0,0,Bars(_Symbol,_Period),rates); //fill the array ZigzagArray FillZigzagArray(0,Bars(_Symbol,_Period)-1); //create the first node TWave *Wave=new TWave; Wave.IndexVertex[0] = 0; Wave.IndexVertex[1] = Bars(_Symbol,_Period)-1; Wave.ValueVertex[0] = 0; Wave.ValueVertex[1] = 0; FirstNode=new TNode; FirstNode.Child=new CArrayObj; FirstNode.Wave=Wave; FirstNode.Text="First node"; string NameWaves="Impulse,Leading Diagonal,Diagonal,Zigzag,Flat,Double Zigzag,Triple Zigzag, Double Three,Triple Three,Contracting Triangle,Expanding triangle"; //call the search for unbegun and incomplete waves function NotStartedAndNotFinishedWaves(Wave,1,FirstNode,NameWaves,0); MessageBox("Analysis is complete"); State=1; ButtonStart.State(false); ChartRedraw(); } // if "Show results" is pressed if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Show results" && State==1) { ArrayResize(LabelArray,ArrayRange(rates,0)); //fill the LabelArray array FillLabelArray(FirstNode); //show the mark-up of the waves on the chart CreateLabels(); State=2; ButtonShow.State(false); ChartRedraw(); } //if "Clear chart" is pressed" if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Clear chart" && State==2) { //clear the waves tree ClearTree(FirstNode); //clear the NodeInfoArray array ClearNodeInfoArray(); //clear the ZigzagArray array ClearZigzagArray(); //clear LabelArray for(int i=0;i<ArrayRange(LabelArray,0);i++) { CArrayObj *ArrayObj=LabelArray[i]; if(CheckPointer(ArrayObj)!=POINTER_INVALID) { for(int j=0;j<ArrayObj.Total();j++) { TLabel *Label=ArrayObj.At(j); delete Label; } ArrayObj.Clear(); delete ArrayObj; } } // delete mark-up from the chart for(int i=ObjTextArray.Total()-1;i>=0;i--) { CChartObjectText *ObjText=ObjTextArray.At(i); ObjText.Delete(); } ObjTextArray.Clear(); State=0; ButtonClear.State(false); ChartRedraw(); } if(id==CHARTEVENT_OBJECT_CLICK && sparam=="Correct the marks" && State==2) { CorrectLabel(); ButtonCorrect.State(false); ChartRedraw(); } }
Elliott Dalgalarının otomatik analizörünün tüm işlevlerini inceledik.
8. Programı iyileştirmenin yolları
MQL5'te yazılmış Elliott Dalga programının otomatik işaretlemesinin birkaç kusuru vardır:
- İşaretleme kurallarını kontrol etmek için kusurlu bir sistem. Örneğin, kurallara göre kontrol ederken, dalgalar arasındaki Fibonacci ilişkileri hem zamana hem de fiyata göre dikkate alınmaz.
- Grafikte bölümlendirilmemiş bölümlerin varlığı (işaretlemedeki boşluklar). Bu, verilen zaman aralığından alınan noktalara göre doğru bir dalga oluşturulamayacağı anlamına gelir. Bu durumdan çıkış yolu, belirli bir dalgayı tanımlamak için nokta sayısını arttırmaktır. Örneğin, dürtüyü bulmak için 6 nokta yerine 8 veya daha fazla nokta arayın.
- İşaretlemenin sonuçları herhangi bir ek bilgi göstermez; örneğin kanallar otomatik olarak oluşturulmaz, hedefler değerlendirilmez vb.
- Bu makalede, dalgalar ağacıyla çalışma uygulaması sağlanmamıştır (işaretlemenin belirli bir sürümünü seçemezsiniz); bu nedenle grafik, işaretleme için birçok seçenekten yalnızca birini gösterir (işaretlemenin ilk sürümü).
- Grafik dalgaların yalnızca bir varyantını göstermesine rağmen, diğer tüm seçenekler bellekte saklanır ve yer işgal eder.
- Program, çok sayıda çubuk olduğunda işlem çok yavaş olduğu için (bir saatlik grafiği işaretlemek saatler sürebilir) grafiklerin Aydan Güne işaretlenmesine odaklanır. Aylık EURUSD grafiğinin bir işaretleme örneği Şekil 18'de gösterilmiştir.
Şekil 18. MQL5'te otomatik analizör tarafından tanımlanan Elliott Dalgaları
Sonuç
Bu makalede, Elliott Dalgalarının otomatik analizinin bir algoritması incelenmiştir. Bu algoritma MQL5 dilinde uygulanmıştır.
Programın yukarıda tartışılan bir takım kusurları vardır ve bunların ortadan kaldırılması için sebep vermektedir. Bu konunun Elliott Dalgaları hayranlarını ilgilendireceğini ve yakında dalgaların otomatik analizini içeren birçok programın ortaya çıkacağını umuyorum.
MetaQuotes Ltd tarafından Rusçadan çevrilmiştir.
Orijinal makale: https://www.mql5.com/ru/articles/260
- Ücretsiz alım-satım uygulamaları
- İşlem kopyalama için 8.000'den fazla sinyal
- Finansal piyasaları keşfetmek için ekonomik haberler
Gizlilik ve Veri Koruma Politikasını ve MQL5.com Kullanım Şartlarını kabul edersiniz