A legnagyobb veszteségű pozi zárása2017-09-28T13:49:02+00:00

Radu.hu Fórum Kérdések az MQL4 programozási nyelvvel kapcsolatban A legnagyobb veszteségű pozi zárása

7 bejegyzés megtekintése - 1-7 / 7
  • Szerző
    Bejegyzés
  • kosza
    Tag
    Bejegyzések száma: 23

    Szia Radu!
    Többször is segítettél már, de most megint kínom van. Nem bírok rájönni, mifenét tolok el. Az lenne a cél, hogy a megnyitott pozikból zárja a legnagyobb veszteségest. Ehhez csináltam egy MaxLoss()-t, ami jó értéket ad vissza:

    double MaxLossLong()
      {
       double MaxLossLong;
       int cnt= OrdersTotal();
       for(i=0; i<cnt; i++)
         {
         if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
          if(OrderSymbol()!=Symbol()) continue;
          type=OrderType();
          if(type==OP_BUY) 
           {
          if(OrderProfit()<=MaxLossLong) MaxLossLong=OrderProfit();    
           }      
         }
         
       return (MaxLossLong);
      }  

    Ezek után ezzel szeretném bezárni:

    `if(ClMaxLoss==1&&LoLot()*ShLot()>0&&ShLot()>=LoLot())
    {

    for(i=0; i<OrdersTotal(); i++) // Order searching cycle
    {
    if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
    if(OrderSymbol()!=Symbol()) continue;
    type=OrderType();
    if(type==OP_BUY)
    {
    RefreshRates();
    if(MaxLossLong()==OrderProfit()&&BuyCnt>1)CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_BID));
    }
    }
    }

    Nem műkszik. Nyilván valami alap dolgot szúrok el, de képtelen vagyok rájönni, mit.
    Köszönöm.

    kosza
    Tag
    Bejegyzések száma: 23

    Nem jól raktam be a záró-kódrészletet. Újra próbálom:

    if(ClMaxLoss==1&&LoLot()*ShLot()>0&&ShLot()>=LoLot())
    {
    
    for(i=0; i<OrdersTotal(); i++) // Order searching cycle 
            {
             if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
             if(OrderSymbol()!=Symbol()) continue;
             type=OrderType();
             if(type==OP_BUY)
               {
                RefreshRates();
                if(MaxLossLong()==OrderProfit()&&BuyCnt>1)CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_BID));            
               }
            }
    }
    Radulovic Attila
    Tag
    Bejegyzések száma: 648

    Ha jól értem, konkrétan a zárással van a problémád, és nem a megfelelő pozíció megtalálásával. A hivatkozott CloseOrder() függvényt nem látom, így arról nem tudok mit mondani 🙂

    Viszont: nem sok cikket írtam programozás témájában, de a zárásról pont igen. Mindenképpen olvasd el azt, szerintem segíteni fog.

    Jelezz majd vissza, hogy mire jutottál.

    kosza
    Tag
    Bejegyzések száma: 23

    Szia! A gond az, hogy ugyanez a CloseOrder() függvény nagyszerűen működik a kód más részein. Pl a psar váltáskor a nyereséges pozik zárása:
    `if(SingleClSARChCl==1&&ClSARPrev<Close[ClSARSignalBar] && ClSARCurr>Close[ClSARSignalBar])
    {
    for(i=0; i<OrdersTotal(); i++) // Order searching cycle
    {
    if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
    if(OrderSymbol()!=Symbol()) continue;
    if(OrderMagicNumber()!=Magic) continue;

    type=OrderType();
    if(type==OP_BUY)
    {
    RefreshRates();
    if(OrderProfit()>0)CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_BID));
    }
    }
    }`
    Azért ideteszem a függvényt:
    bool CloseOrder(int ticket,double lot,double price)
    {
    if(!OrderSelect(ticket, SELECT_BY_TICKET)) return(false);
    if(OrderCloseTime() > 0) return(false);

    int dig=MarketInfo(OrderSymbol(),MODE_DIGITS);
    string _lot=DoubleToStr(lot,2);
    string _price=DoubleToStr(price,dig);

    bool res=OrderClose(ticket,lot,price,Slippage,clClose);
    if(res)
    {
    Sleep(SleepOk);
    return (res);
    }

    int code=GetLastError();
    Sleep(SleepErr);

    return (false);
    }`

    Ideteszem újra a kicsit átfogalmazott problémás részt:

    if(ClMaxLoss==1&&LoLot()*ShLot()>0&&SellCnt>1)  // ha long és short is van és shortból több, mint egy darab
    {
    for(i=0; i<OrdersTotal(); i++) // Order searching cycle 
            {
             if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
             if(OrderSymbol()!=Symbol()) continue;
             if(OrderMagicNumber()!=Magic) continue;
             type=OrderType();
             if(type==OP_SELL)
               {
                RefreshRates();            
                if(MaxLossShort()==OrderProfit())CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_ASK));  
               // ha olyat talál, aminek a vesztesége megegyezik a legnagyobb veszteségű short pozival, zárja le
               
               }
            }
    }

    Ehelyett azt csinálja, hogy nem a legnagyobb veszteségű pozit zárja, hanem az utolsónak megnyitottat.
    Ha a RefreshRates() utáni sort kicserélem erre:

    if(Ask-OrderOpenPrice()>=Delta*Point*fpc())CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_ASK));            
               // ha az ask és megnyitott pozi nyitási ára közötti különbség nagyobb, mint "Delta" pip, zárja le a pozit;
               // (az fpc() a bróker digitjétől függen ad vissza 10-et vagy százat)

    ez működik, a megfelelő pozikat zárja le.
    Ezek szerint a hiba ott van valahol a kicserélt sorban. Nem segít az sem, hogyha az “orderprofit” helyett a nyitó és az aktuális “ask” segítségével határozom meg a veszteséget.
    Előre is köszönöm a segítségedet.

    kosza
    Tag
    Bejegyzések száma: 23

    Nna, az első két kódrészletet újra küldöm. Nem vágom, hogy miért szövegként tette be. Bocs. Tehát sar váltásra pozi zárás

    if(SingleClSARChCl==1&&ClSARPrev>Close[ClSARSignalBar] && ClSARCurr<Close[ClSARSignalBar])
       {
          for(i=0; i<OrdersTotal(); i++) // Order searching cycle 
            {
             if(!OrderSelect(i,SELECT_BY_POS,MODE_TRADES)) continue;
             if(OrderSymbol()!=Symbol()) continue;
             if(OrderMagicNumber()!=Magic) continue;
    
             type = OrderType();
             if(type == OP_SELL)
               {
                RefreshRates();
    
                if(OrderProfit()>0)CloseOrder(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_ASK));
               }
            }
         }

    a záró fgv

    bool CloseOrder(int ticket,double lot,double price)
      {
       if(!OrderSelect(ticket, SELECT_BY_TICKET)) return(false);
       if(OrderCloseTime() > 0) return(false);
    
       int dig=MarketInfo(OrderSymbol(),MODE_DIGITS);
       string _lot=DoubleToStr(lot,2);
       string _price=DoubleToStr(price,dig);
    
       bool res=OrderClose(ticket,lot,price,Slippage,clClose);
       if(res) 
         {
          Sleep(SleepOk);
          return (res);
         }
    
       int code=GetLastError();
       Sleep(SleepErr);
    
       return (false);
      }
    Radulovic Attila
    Tag
    Bejegyzések száma: 648

    Én a linkelt cikkben bemutatott kódot használom. Nincs most kapacitásom minden lehetséges hibát végiggondolni a kódod kapcsán, ott a teljes megoldást át tudod nézni.

    Kapkodós észrevételeim:

    • a linkelt cikkben beszélek a ciklusokkal kapcsolatos problémákról, azt mindenképp nézd át
    • a Sleep() sikeres zárás esetén felesleges, nem tudom, mi célból van bent
    • a zárófüggvénybe én nem vinném be az aktuális árat, mert menet közben az változhat; használd inkább a zárandó típustól függően a MODE_BID és MODE_ASK árakat
    • ha nem sikerül zárnod, akkor tudni kellene, hogy miért nem sikerül; a GetLastError() közvetlenül az OrderClose után jöjjön, a res false ágában. Írasd ki, és nézd meg, hogy mi a nyűgje.
    kosza
    Tag
    Bejegyzések száma: 23

    O.K. Köszönöm

7 bejegyzés megtekintése - 1-7 / 7

A hozzászóláshoz jelentkezz be!

Adhatok Neked még több ingyenes tartalmat?

Értesítelek hetente megjelenő új tartalmaimról.

Hozzájárulok, hogy az adatvédelmi nyilatkozat szerint biztonságosan kezeld megadott adataimat, valamint hasznos anyagokat és egyedi ajánlatokat küldj nekem termékeiddel, szolgáltatásaiddal kapcsolatban e-mailben