Zum Inhalt springen
View in the app

A better way to browse. Learn more.

#T/N/X/T

A full-screen app on your home screen with push notifications, badges and more.

To install this app on iOS and iPadOS
  1. Tap the Share icon in Safari
  2. Scroll the menu and tap Add to Home Screen.
  3. Tap Add in the top-right corner.
To install this app on Android
  1. Tap the 3-dot menu (⋮) in the top-right corner of the browser.
  2. Tap Add to Home screen or Install app.
  3. Confirm by tapping Install.

Einstieg zu MT4 Programmierung

Geschrieben

Hallo,

 

ich hätte da mal eine Frage:

Was benötigt man um überhaupt für mt4 Programmieren zu können?

Welche Standartsoftware ist damit gemeint.

 

Woher bekomme ich diese?

 

Grüsse

Jörg

  • Antworten 269
  • Aufrufe 81Tsd
  • Erstellt
  • Letzte Antwort

Top-Benutzer in diesem Thema

Most Popular Posts

  • Also wenn dein Code im Indikator aufgerufen wird, brauchst du auf jedem Fall die Funktion iBarShift, wie ich es oben beschrieben habe, aus dem ExpertAdvisor wird auch so funktionieren. Schau wirklich

  • die folgene Erklärung von Funktionen bezieht sich nur auf MQL4!   Was ist start() ? eine Funktion!   Alles was Arbeitet findet immer in Funktionen statt. Ausserhalb von Funktionen geht nix.   bei MQL

  • Das ist eigentlich kein Bug Du gibst in dem iHigh(NULL, 15, 1) in dem Parameter Barshift 1 an, das ist falsch. In dem Strategietester wird dieser Bar immer den gleichen Wert zurückgeben, nämlich Hi

Veröffentlichte Bilder

Featured Replies

Geschrieben

Beides schöne Antworten, aber ich hab gar nicht Tradingtechnisch sondern rein programmier/verständnisstechnisch gedacht.

 

zB folgender Code:

 

double ma1,ma2;

ma1= iMA(NULL,0,10,0,MODE_SMA,PRICE_CLOSE,1);
ma2= iMA(NULL,0,50,0,MODE_SMA,PRICE_CLOSE,1);

if(Crossed(ma1,ma2) == 2) {
 //cross nach unten zB Short einstieg
} else if(Crossed(ma1,ma2) == 1) {
 //cross nach oben zB Long einstieg
}

 

Tut der Code das was er offensichtlich soll?

Bearbeitet von Mythos
Konstanten korrigiert

Geschrieben

Wäre nach meinem Verständnis genau andersum: ma1 > m2 -> long, für short umgekehrt.

So ist es zumindest auf Funktionsebene implementiert.

Aber ich befürchte, Du meinst was anderes ...

 

 

Geschrieben

Wäre nach meinem Verständnis genau andersum: ma1 > m2 -> long, für short umgekehrt.

So ist es zumindest auf Funktionsebene implementiert.

Aber ich befürchte, Du meinst was anderes ...

 

Stimmt, mein Fehler. 1 und 2 sind aber auch nicht wirklich gute Konstanten um rauf und runter zu codieren. Da wär 1 (für cross up) und -1 (für cross down) irgendwie logischer.

Aber wie du schon befürchtest, ich mein wiedermal nicht die Tradingebene sondern rein die Programmierseite.

 

Angenommen innerhalb er Schleifen würden zB Orders (also long bei cross up, short bei cross down) eröffnet, würden in den Resultaten Long und Short Orders auftreten?

Geschrieben

Wat isn nu? :chief:

 

Angenommen innerhalb er Schleifen würden zB Orders (also long bei cross up, short bei cross down) eröffnet, würden in den Resultaten Long und Short Orders auftreten?

 

Ok, angenommen eine long Order ist offen, es kommt ein short Signal, dann wird mit der short Order die long Order geschlossen und es würde keine short Order eröffnet. Somit gibt es keine offenen Orders in beide Richtungen, es sei denn man programmiert das anders.

 

Meinst Du das? :kaffee:

Geschrieben

Ok, angenommen eine long Order ist offen, es kommt ein short Signal, dann wird mit der short Order die long Order geschlossen und es würde keine short Order eröffnet. Somit gibt es keine offenen Orders in beide Richtungen, es sei denn man programmiert das anders.

 

Meinst Du das? :kaffee:

 

Nein. Ich sehe es war gut das ich die Frage gestellt hab ;)

 

Gehen wirs langsam durch.

 

Sagen wir, wir starten an einem Punkt wo ma1 = 10 und ma2 = 20 ist.

Innerhalb der Cross-Funktion steht last_direction also auf 2. (btw. current_direction muss nicht static sein hier)

Jetzt kommt ein neuer Tick und ma1 = 25 und ma2 = 20.

Jetzt wirds haarig also Zeile für Zeile:

if(Crossed(ma1,ma2) == 2) { 

Crossed(25,20) wird aufgerufen, line1 (25) ist größer als line2 (20) also current_direction= 1.

Die if ist erfüllt, es wird last_direction auf 1 gesetzt und 1 zurückgegeben.

Im Ablauf wird jetzt der Rückgabewert von Crossed(25,20) (also 1) mit 2 verglichen, stimmt nicht also überspringen wir den if-Body und kommen zur else if Abfrage:

} else if(Crossed(ma1,ma2) == 1) {

Also wieder Crossed(25,20) aufrufen. Erneut wird current_direction auf 1 gesetzt (kein Wunder), aber da last_direction vom letzten Aufruf bereits 1 ist ist die if-Bedingung nicht erfüllt, wir überspringen den if-body und geben 0 zurück. 0 verglichen mit 1 ist wieder nicht wahr und wir überspringen auch diesen Block.

 

In Summe: Kreuzung nach oben, aber der EA hats nicht mitgekriegt.

 

Fazit: Diese Variante der Crossfunktion, zeigt ein Kreuzen genau beim ersten Aufruf mit Werten nach dem Cross an. Für die Funktion entspricht jeder Aufruf der Funktion einem neuen Zeitpunkt. Also wenn ihr diese Funktion verwenden wollt: einmal im start() aufrufen, Wert speichern und diesen verwenden. Sonst wird das nix.

 

hth

Geschrieben

hallo zusammen,

 

zuerst muss ich euch allen hier ein großes kompliment machen,

wirklich toll, was ihr hier leistet!!! :respekt:

 

bin auch dabei mql4 zu verstehen und bastel eben meinen ersten ea,

was zugegeben schwerer ist als ich gedacht habe, aber wie sagt schon

ein altes sprichwort? "aller anfang ist schwer"

 

es wäre klasse, wenn ein profi sich mal meinen code ansehen würde,

denn dieser teil funktioniert nicht so, wie ich das gerne hätte. :sad:

 

 


// Tagesziel erreicht?                                                        

  int Orders_History_Total=OrdersHistoryTotal();         
     for (int OHT=Orders_History_Total-1; OHT>=0; OHT--) 
        {						  
        OrderSelect(OHT,SELECT_BY_POS,MODE_HISTORY);
        if (OrderSymbol() == Symbol())                    
           {  				                  
           if ((TimeDayOfYear(OrderOpenTime()) == DayOfYear()) && (TimeYear(OrderOpenTime()) == Year()))
              {					  
              if (OrderProfit() >= TagesZiel)            
              Comment ("Tagesziel erreicht");            
              return (0);                                
              }
           }		
        }			

 

das TagesZiel ist mit einer externen globalen variablen auf 1.000 (zum testen) gesetzt.

 

Es wird täglich immer nur 1x gehandelt. Mein Ziel ist es aber, wenn das TagesZiel erreicht

wurde, dann den handel erst am folgenden Tag fortsetzen.

 

Kann mir bitte jemand helfen? Vielen Dank vorab! :top:

 

MfG

Nelly

Geschrieben

Hallo Nelly,

 

Herzlich Willkommen hier im Forum. :door:

 

denn dieser teil funktioniert nicht so, wie ich das gerne hätte. :sad:

 

 

Was funktioniert denn nicht? Wenn ich mir den Code anschaue, dann sollte der Kommentar ausgegeben werden, sobald eine Position gefunden wurde, die größer als deine externe Vergleichsvariable ist. Denke das ist so gewollt. Du kannst so natürlich nur immer eine historische Position abfragen. Wenn du beispielsweise heute schon 2 Positionen mit je 500€ Gewinn hattest, dann wirst du eine neue Position auf diese Weise natürlich nicht sperren...

 

VG,

Wogo

Geschrieben

              if (OrderProfit() >= TagesZiel)            
              Comment ("Tagesziel erreicht");            
              return (0);                                

Da fehlen Klammern. Daher geht er immer mit einem Return raus. Also:

              if (OrderProfit() >= TagesZiel)            
              {
               Comment ("Tagesziel erreicht");            
               return (0);                                
              }

 

Aber erstmal: herzlich willkommen, Nelly :drinkbeer: Und beachte bitte das, was Wogo gesagt hat: es wird nicht die Summe der Tagestrades genommen, sondern es wird der erste Trade geprüft, den er an dem Tag findet.

Geschrieben

Hallo Nelly,

 

Herzlich Willkommen hier im Forum. :door:

 

 

 

Was funktioniert denn nicht? Wenn ich mir den Code anschaue, dann sollte der Kommentar ausgegeben werden, sobald eine Position gefunden wurde, die größer als deine externe Vergleichsvariable ist. Denke das ist so gewollt. Du kannst so natürlich nur immer eine historische Position abfragen. Wenn du beispielsweise heute schon 2 Positionen mit je 500€ Gewinn hattest, dann wirst du eine neue Position auf diese Weise natürlich nicht sperren...

 

VG,

Wogo

 

hallo wogo,

 

vielen dank für deine nachricht, ging ja echt rasent schnell ... :ferrari:

 

ich möchte, dass der ea bei einem profit/tag von 1.000 eur aufhört zu arbeiten.

 

so wie er jetzt ist, arbeitet er nur 1x am tag & stellt dann die arbeit ein

(unabhängig davon, wie hoch der Tagesprofit ist).

 

wenn der angehängte code im ea weggelassen wird, dann handelt er mehrfach am tag,

aber mit nur 1x (wie gesagt, egal ob 1.000 eur oder 1 eur).

 

die 1.000 habe ich auch nur angegeben um zu sehen ob es funktioniert,

was er leider nicht macht.

 

mfg

nelly

Geschrieben

Probiers mal so:

  double Tagesprofit=0;
  int Orders_History_Total=OrdersHistoryTotal();         
     for (int OHT=Orders_History_Total-1; OHT>=0; OHT--) 
        {                                                
        OrderSelect(OHT,SELECT_BY_POS,MODE_HISTORY);
        if (OrderSymbol() == Symbol())                    
           {                                             
           if ((TimeDayOfYear(OrderOpenTime()) == DayOfYear()) && (TimeYear(OrderOpenTime()) == Year()))
              {               
              Tagesprofit=Tagesprofit+OrderProfit();                           
              if (Tagesprofit >= TagesZiel)  
              {          
                Comment ("Tagesziel erreicht");            
                return (0);       
              }                         
              }
           }           
        }         

Geschrieben

Probiers mal so:

  double Tagesprofit=0;
  int Orders_History_Total=OrdersHistoryTotal();         
     for (int OHT=Orders_History_Total-1; OHT>=0; OHT--) 
        {                                                
        OrderSelect(OHT,SELECT_BY_POS,MODE_HISTORY);
        if (OrderSymbol() == Symbol())                    
           {                                             
           if ((TimeDayOfYear(OrderOpenTime()) == DayOfYear()) && (TimeYear(OrderOpenTime()) == Year()))
              {               
              Tagesprofit=Tagesprofit+OrderProfit();                           
              if (Tagesprofit >= TagesZiel)  
              {          
                Comment ("Tagesziel erreicht");            
                return (0);       
              }                         
              }
           }           
        }         

 

hallo WOGO,

 

vielen dank für deine hilfe, es klappt 1a (allerding musste ich noch ein

"-1" einfügen bei " int Orders_History_Total=OrdersHistoryTotal();"

die zeile ist somit wie folgt richtig " int Orders_History_Total=OrdersHistoryTotal()-1;"

 

dann funktioniert´s 1a!!!!

 

hier der komplette code für alle, die nach erreichen eines festen tagesziels den ea schlafen schicken wollen:

 

 double Tagesprofit=0;
     int Orders_History_Total=OrdersHistoryTotal()-1;         
        for (int OHT=Orders_History_Total-1; OHT>=0; OHT--) 
        {                                                
        OrderSelect(OHT,SELECT_BY_POS,MODE_HISTORY);
        if (OrderSymbol() == Symbol())                    
           {                                             
           if ((TimeDayOfYear(OrderOpenTime()) == DayOfYear()) && (TimeYear(OrderOpenTime()) == Year()))
              {               
              Tagesprofit=Tagesprofit+OrderProfit();                           
              if (Tagesprofit >= TagesZiel)  
                 {          
                 Comment ("Tagesziel erreicht");            
                 return (0);       
                 }                         
              }
           }           
        }         

 

vielen herzlichen dank WOGO!!!

Geschrieben

vielen herzlichen dank WOGO!!!

Naja,

mindestens 50% des Dankes muß ich an Rainworm weitergeben, der ja den eigentlichen Fehler gefunden hat. :wub:

Geschrieben

Da fehlen Klammern. Daher geht er immer mit einem Return raus. Also:

              if (OrderProfit() >= TagesZiel)            
              {
               Comment ("Tagesziel erreicht");            
               return (0);                                
              }

 

Aber erstmal: herzlich willkommen, Nelly :drinkbeer: Und beachte bitte das, was Wogo gesagt hat: es wird nicht die Summe der Tagestrades genommen, sondern es wird der erste Trade geprüft, den er an dem Tag findet.

 

hallo RAiNWORM,

 

vielen herzlichen dank auch an dich für deine mühe & das herzliche willkommen hier im forum!

 

an den klammern lag es nicht, hab´s eben noch einmal ausprobiert,

aber du hast natürlich recht, die fehlten auch ... :top:

 

es lag an dem -1 was fehlte ... und natürlich an der umstellung durch WOGO!

 

dieses forum ist echt klasse, hoffe auch bald einem newbie helfen zu können,

die materie ist echt nicht einfach, von zeit zu zeit raucht mir wirklich der kopf ... :doink:

Geschrieben

Moin moin,

 

muss ihmo noch was in die "Start", damit er den Handel für den Tag einstellt:

 

if (Tagesprofit >= TagesZiel)

return (0);

Bei mir läuft es im Mom allerdings andersrum. :plorar1: :laugh:

 

if (st_day_profit

return(0); // auf neuen Tag warten

 

Wollkommen in Club Nelly. :chocala:

Geschrieben

allerding musste ich noch ein

"-1" einfügen bei " int Orders_History_Total=OrdersHistoryTotal();"

die zeile ist somit wie folgt richtig " int Orders_History_Total=OrdersHistoryTotal()-1;"

Das funktioniert wirklich? Ich würde spontan sagen, dass dadurch eine geschlossene Order weniger geprüft wird, da du in der for-Schleife danach nochmals -1 rechnest. Wundert mich :gum:

Geschrieben

Das funktioniert wirklich? Ich würde spontan sagen, dass dadurch eine geschlossene Order weniger geprüft wird, da du in der for-Schleife danach nochmals -1 rechnest. Wundert mich :gum:

 

ja, es funktioniert wirklich!!! (gott sei dank, hab schon ne weile daran "gefeilt") :-))

 

frag mich aber nicht nicht warum ... hauptsache es funzt

Geschrieben

Wollkommen in Club Nelly. :chocala:

 

Hier mal eine Funktion, wie sie bei mir auch in "echten" EAs eingesetzt wird:

 

double get_day_profit() 
{
double result = 0;
 
for (int ii = OrdersHistoryTotal()-1; ii >= 0; ii--)
{
 if (OrderSelect(ii, SELECT_BY_POS, MODE_HISTORY))
 {
  datetime oct = OrderCloseTime();
  if( 
     (oct != 0) &&
     (OrderMagicNumber() == magicnumber)        &&   // bei Bedarf rausnehmen (wenn magicnumber nicht beachtet werden soll)
     (OrderSymbol()      == Symbol())           &&   // bei Bedarf rausnehmen (wenn Tagessaldo unabhängig vom Symbol betrachtet werden soll)
     (TimeDay(oct)       == TimeDay(Time[0]))   &&
     (TimeMonth(oct)     == TimeMonth(Time[0])) &&
     (TimeYear(oct)      == TimeYear(Time[0]))  
     )
  {
   result = result + OrderProfit();
  }
 }
} 
return(result);
}

 

Somit kann man im Programmcode diese Funktion aufrufen:

 

if (get_day_profit() > 1000) return(0); // bei 1000 EUR Gewinn rausgehen
if (get_day_profit() < -1000) return(0); // bei 1000 EUR Verlust rausgehen

 

@Nelly: übrigens überprüfst du in deinem Code nicht den Monat. Somit würde er bspw. am 08.03.2011 nicht handeln, wenn du am 08.02.2011 über 1000 EUR warst.

Geschrieben

Hier mal eine Funktion, wie sie bei mir auch in "echten" EAs eingesetzt wird:

 

double get_day_profit() 
{
double result = 0;
 
for (int ii = OrdersHistoryTotal()-1; ii >= 0; ii--)
{
 if (OrderSelect(ii, SELECT_BY_POS, MODE_HISTORY))
 {
  datetime oct = OrderCloseTime();
  if( 
     (oct != 0) &&
     (OrderMagicNumber() == magicnumber)        &&   // bei Bedarf rausnehmen (wenn magicnumber nicht beachtet werden soll)
     (OrderSymbol()      == Symbol())           &&   // bei Bedarf rausnehmen (wenn Tagessaldo unabhängig vom Symbol betrachtet werden soll)
     (TimeDay(oct)       == TimeDay(Time[0]))   &&
     (TimeMonth(oct)     == TimeMonth(Time[0])) &&
     (TimeYear(oct)      == TimeYear(Time[0]))  
     )
  {
   result = result + OrderProfit();
  }
 }
} 
return(result);
}

 

Somit kann man im Programmcode diese Funktion aufrufen:

 

if (get_day_profit() > 1000) return(0); // bei 1000 EUR Gewinn rausgehen
if (get_day_profit() < -1000) return(0); // bei 1000 EUR Verlust rausgehen

 

@Nelly: übrigens überprüfst du in deinem Code nicht den Monat. Somit würde er bspw. am 08.03.2011 nicht handeln, wenn du am 08.02.2011 über 1000 EUR warst.

 

vielen dank für den hinweis mit dem monat ...

 

da kann man mal sehen wie weit der weg noch ist,

stehe am anfang & sehe den wald vor lauter bäumen nicht ... :cry:

 

nehme dann wohl lieber deinen code, der ist wenigstens fehlerfrei :top:

Geschrieben

nehme dann wohl lieber deinen code, der ist wenigstens fehlerfrei :top:

Nur noch als Anmerkung.

Das funktioniert dann aber nur, wenn du nur auf einem Symbol handelst. In Rainworms Code wird nämlich nicht abgefragt, ob die aus der Historie ausgelesene Position auch dem aktuellen Symbol entspricht...

Geschrieben

Nur noch als Anmerkung.

Das funktioniert dann aber nur, wenn du nur auf einem Symbol handelst. In Rainworms Code wird nämlich nicht abgefragt, ob die aus der Historie ausgelesene Position auch dem aktuellen Symbol entspricht...

 

ich werd noch wahnsinnig ... :cry:

 

auf was man alles achten muss is echt unglaublich,

vielen dank noch einmal auch an dich für den hinweis :top:

Geschrieben

ich werd noch wahnsinnig ... :cry:

Glaube ich gerne, ich muß beim lesen schmunzeln, wenn die Programmierer immer noch einen rauf packen.

 

Hast du 1 gedacht ? > ja

Hast du an 2 gedacht ? > ja

......

Hast du an 44 gedacht ? > ja

 

und dann hat man fast das Gefühl das der Programmierer das bis zur Nr.163 durchhält. :laugh:

Bist du endlich mal nein sagen musst...

Geschrieben

Hast du 1 gedacht > ja

hast du an 2 gedacht > ja

Wobei es immer hilfreich ist zu wissen, wie der andere denkt.

Soll nämlich der Gesamtprofit pro Tag über alle Symbole betrachtet werden, dann ist Rainworms Code natürlich wieder richtig :tongue:

 

Ja, ja,

ich hör schon auf. :pfue:

Geschrieben

Ja, ja,

ich hör schon auf. :pfue:

War auch ganz sicher keine Kritik,

aber grade als Laie liest sich da echt witzig, wenn immer noch etwas zusätzliches beachtet werden muß.

 

Ich finde es auch unglaublich was da alles beachtet werden muß - Vola weiß schon warum das

bei ihm in diesem Leben wohl nicht mehr mit dem proggen klappen wird.... :blackjack:

Geschrieben

und dann hat man fast das Gefühl das der Programmierer das bis zur Nr.163 durchhält. :laugh:

Achja: mein Code funktioniert nur bis Timeframe D1. Alles über der Tagesdarstellung geht nicht. Wer rausfindet wieso, bekommt ein Thanks :wink2:

 

Das funktioniert dann aber nur, wenn du nur auf einem Symbol handelst. In Rainworms Code wird nämlich nicht abgefragt, ob die aus der Historie ausgelesene Position auch dem aktuellen Symbol entspricht...

Und was bedeutet dann bei mir OrderSymbol() == Symbol() ? :tongue:

Dein Kommentar

Du kannst jetzt schreiben und Dich später registrieren. Wenn Du ein Konto hast, melde Dich jetzt an, um unter Deinem Benutzernamen zu schreiben.

Gast
Auf dieses Thema antworten...

Account

Navigation

Suche

Suche

Configure browser push notifications

Chrome (Android)
  1. Tap the lock icon next to the address bar.
  2. Tap Permissions → Notifications.
  3. Adjust your preference.
Chrome (Desktop)
  1. Click the padlock icon in the address bar.
  2. Select Site settings.
  3. Find Notifications and adjust your preference.