Metatrader Forum | Forex Expert-Advisor | Broker & Forex Tools

Metatrader Forum | Forex Expert-Advisor | Broker & Forex Tools (http://www.expert-advisor.com/forum/index.php)
-   Programmierung MQL4 (http://www.expert-advisor.com/forum/forumdisplay.php?f=220)
-   -   martingales MoneyManagement (http://www.expert-advisor.com/forum/showthread.php?t=5869)

piptrade 26.09.17 18:07

martingales MoneyManagement
 
Liebe Programmier-"Gemeinde",

habe im letzten 1/2 Jahr meinen ersten kleinen robot geschrieben, welcher bis zum heutigen Tag, - entsprechend der Auswertungen des strategy-testers, - ein Profit-Losses-Verhältnis von ca. 60 : 40 aufweist. Um das "Teil" weiterhin zu optimieren, soll nun eine zweite Strategie, ein Hedging-Part und ein martingales Money Management ergänzt werden.

Um den letztgenannten Code zu realisieren, habe ich als erstes versucht, die Anzahl der bestehenden offenen Positionen eines Vehikels (openOrders) zu bestimmen (Calculate open positions). Dieser Wert wird abschließend mit "return" zurückgegeben.
Als zweites (MM - Calculate martingale lot size ...) soll dann die Berechnung von "lot" unter Verwendung von "extern Lot" und "MaximumRisk" erfolgen. - Und dies für den ersten zu öffnenden Trade.
Abschließend soll dann das martingale System zur Anwendung kommen, in dem die Anzahl der ggf. offenen Positionen (openOrders) aufgegriffen und die lot für 2, 3, ... usw. offene Positionen berechnet wird.

Alles in Allem sieht das "Teil" so aus:
Code:

//+==================================================================================+
//| Calculate open positions                                                        |
//+==================================================================================+

int CalculateCurrentOrders(string symbol)
  {
  int buys=0,sells=0;
//---
  for(int i=0;i<OrdersTotal();i++)
    {
      if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES)==false) break;
      if(OrderSymbol()==Symbol() && OrderMagicNumber()==OrderMagicNumber)
        {
        if(OrderType()==OP_BUY)  buys++;
        if(OrderType()==OP_SELL) sells++;
        }
    }
    if(openOrders>0) openOrders = buys+sells;
  return (openOrders);

//+===================================================================================+
//| MoneyManagement - Calculate martingale lot size for open positiones              |           
//|===================================================================================+
double LotsOptimized()
  {
  double lot=Lots;
 
//--- select lot size
  lot=NormalizeDouble(AccountFreeMargin() *MaximumRisk / 100, 2);  //  2 = Digits for DAX

//--- calculate martingale steps
  if(ProfitFactor>0)
    {
//-- MathPow(double base,double exponent); = bereits im Editor implementiert
//-- Formel für Zahlenreihe der Verdopplung: a(openOrders) = 2 *2(hoch openOrders - 1)
    lot = NormalizeDouble(lot *2 *MathPow(2,openOrders - 1),2);
    } 
//--- return lot size
  if(lot<0.01) lot=0.01;
  return(lot);
  } 
//+=======================================================================================+

Nach dem Kompellieren: 0 errors / 0 warnigs ! Zumindest diese Aussage stimmt mich erst einmal optimistisch. Ob aber alles, wie gewollt, funktioniert oder ob ich Änderungen/Verbesserungen vornehmen kann oder muss ... ?

An dieser Stelle wäre ich für Eure Unterstützung sehr dankbar.

LG. piptrade

mat 08.10.17 17:18

Hallo!

Was ist denn Deine Frage?

LG M.

piptrade 08.10.17 19:09

Hi mat,

vorab herzlichen Dank für Dein Interesse und Deine Anfrage.

Es ist für mich das erste Mal, dass ich einen solchen Money Management-Code schreibe und da stellt sich einfach die Frage, in wie weit die Herangehensweise richtig ist und ob der Code ggf. verbessert/optimiert werden könnte.

Und wenn Verbesserungen - welche.

Ich hoffe damit meine Fragestellung konkretisiert zu haben.

LG. piptrade

mat 08.10.17 20:30

Ich schicke vorweg: weder bin ich ein großer Trading-Experte, noch MQL-Spezialist! Aber ich programmiere seit über 30 Jahren und kann Dir daher ein paar allgemeine Tipps geben. (Kommentare im Code)

Code:

//+==================================================================================+
//| Calculate open positions                                                        |
//+==================================================================================+

int CalculateCurrentOrders(string symbol)
  {
  int buys=0,sells=0;
//---
  for(int i=0;i<OrdersTotal();i++)
    {
          // OrderSelect ist schon boolean, das muss nicht mehr mit true oder false verglichen werden.
          // (Das ! heißt ›not‹)
      if( !OrderSelect(i,SELECT_BY_POS,MODE_TRADES) ) break;
          // Wo ist die Variable ›OrderMagicNumber‹ deklariert? (Nicht in diesem Codestück!)
          // Jedenfalls würde ich auf ›strict‹ schalten
      if(OrderSymbol()==Symbol() && OrderMagicNumber()==OrderMagicNumber)
        {
        if(OrderType()==OP_BUY)  buys++;
                // Das if kann eingespart werden, falls OrderType()==OP_BUY war.
                // Die Optimierung ist (vernachlässigbar) *winzig*, tritt aber immerhin in einer Schleife auf.
        ELSE if(OrderType()==OP_SELL) sells++;
        }
    }
        // wo ist openOrders deklariert? Wieso sollte es >0 sein? Bzw. wie wird es jemals >0?
    if(openOrders>0) openOrders = buys+sells;
  return (openOrders);

//+===================================================================================+
//| MoneyManagement - Calculate martingale lot size for open positiones              |           
//|===================================================================================+
double LotsOptimized()
  {
  double lot=Lots;
 
//--- select lot size
        // Tipp: Leg Dir eine Systematik zurecht, welche Variablen mit Großbuchstaben beginnen.
        // (bei mir: die Input-Parameter fangen mit Großbuchstaben an, alle lokalen Variablen klein.
        // Mach klar, dass Du keine integer-Division willst (100.)
  lot=NormalizeDouble(AccountFreeMargin() * MaximumRisk / 100., 2);  //  2 = Digits for DAX

//--- calculate martingale steps
  if(ProfitFactor>0)
    {
//-- MathPow(double base,double exponent); = bereits im Editor implementiert
//-- Formel für Zahlenreihe der Verdopplung: a(openOrders) = 2 *2(hoch openOrders - 1)
    lot = NormalizeDouble(lot *2 *MathPow(2,openOrders - 1),2);
    } 
//--- return lot size
  if(lot<0.01) lot=0.01;
  return(lot);
  } 
//+=======================================================================================+

Alles nur Vorschläge und Anregungen!

LG

piptrade 09.10.17 15:52

Hallo, mat,

suuuper, dass Du Dich der Angelegenheit sofort und soooo umfänglich angenommen hast. Danke, Deine Hinweise sind wirklich „Gold“ wert.

Im Folgenden aber zu diesen „Randnotizen“ konkret:
A) Calculate open positions
1. „ if( ! OrderSelect(i,SELL, … “ - boolean bzw. das Ausrufezeichen wurden verstanden
2. „OrderMagicNumber“ und „openOrders“ wurden bereits global deklariert
3. Die Einsparung „if(OrderType()==OP_BUY) buys++;“ und der „else“-Zusatz in der nachfolgenden Zeile
sind auch soweit klar
4. FRAGE: Weshalb sollte „openOrders()“ nicht „ > 0“ erreichen ?
B) MoneyManagement – Calculate …
1. der Tipp mit den Variablen in Groß- bzw. Kleinbuchstaben – sehr gut, werde ich zukünftig so nutzen
2. integer-Division kann mit dem Punkt hinter der „100.“ ausgeschlossen werden ? - Auch gut !

Bis auf die o.a. eine Frage wurde alles verstanden und 1 : 1 umgesetzt. Thanks !
Dennoch: weshalb sollte „openOrder()“ nicht „ > 0“ sein können ? Im Abschnitt A) werden doch offene buys und sells zusammengezählt und sind dann doch „ > 0“ !?

Würde mich über ein nochmaliges kleines Statement freuen.

LG. piptrade

mat 09.10.17 16:31

Gerne!

openOrders wird nur dann ausgerechnet und zugewiesen, *wenn* openOrders>0 ist! Wie soll das das allererste mal passieren?

Oder habe ich etwas ver- bzw. überlesen?

LG

piptrade 11.10.17 15:20

Hi, mat,

sinnvoller Weise brauche ich doch weigstens "1" openOrder ---> also > 0 , wenn ALLE sells und buys addiert und dann als Exponent zugewiesen werden sollen.
>= 0 hätte in meinen Augen den gleichen Effekt; - hier wird dann aber schon gezählt, wo es noch gar nichts zu zählen gibt; - oder ?


LG. piptrade

mat 11.10.17 16:08

Das ist vom Gedanken her richtig, aber die Variable openOrders ist ja erst einmal 0! Daher wird das if nie betreten (!!), die Zuweisung findet gar nicht statt und openOrders bleibt 0!

(Es sei denn, openOrders wird irgendwo außerhalb des Codesegments gesetzt, das du herein gestellt hast!)

LG

traderdoc 11.10.17 17:27

Ja, dann schreibe doch einfach:

Code:

return (buys+sells);

Oder wenn die 0 ausgeschlossen sein soll:

if (buys + sells > 0) ...

Oder

if (buys > 0 || sells > 0) ...

Dann fällt das ganze openOrders weg!

traderdoc


Alle Zeitangaben in WEZ +2. Es ist jetzt 03:23 Uhr.

Powered by vBulletin® Version 3.8.5 (Deutsch)
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
SEO by vBSEO 3.6.1
Powered by vBCMS® 2.7.0 ©2002 - 2024 vbdesigns.de
Copyright ©2009 - 2023 by Expert-Advisor.com - Das Metatrader Forum