Доброго всем времени суток.
Нужна помощь в коррекции функций советника.
Идея такова: поступил сигнал Sell > открылся ордер, поступил сигнал Buy > открылся ордер.
В рынке одновременно и Buy и Sell.
Сетка через 35 пунктов с увеличением лота отдельно для Sell ордеров и отдельно для Buy ордеров.
НО! В какой-то момент раздельное увеличение лота дает сбой.
Грешу на две функции: FindLastOrderLot() и Lot()
Подскажите пожалуйста, где я «дал маху»?
//--- Inputs
extern double Lots = 0.1; // торговый объем ордера
extern double Risk =3000; // Risk
extern double KLot = 2; // увеличение лота
extern int StopLoss = 0; // лось
extern int TakeProfit = 100; // язь
extern int TrailingStop = 0; // трал
extern int TrailingStep = 0; // трал степ
extern double Profit = 0.29; // Profit-Recovery
extern int Slip = 10; // реквот
extern int CloseSig = 0; // 1-закрытие по сигналу
extern int Magic = 123; // магик
extern int StepOrder =350;
extern int Count =9; //кол-во ореров
extern int Shift = 1; // бар индикатора
extern int BBPeriod = 35;
extern double BBDev = 2.2;
datetime t=0;
double MINLOT,MAXLOT;
//+------------------------------------------------------------------+
//| Expert initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
//---
MINLOT = MarketInfo(Symbol(),MODE_MINLOT);
MAXLOT = MarketInfo(Symbol(),MODE_MAXLOT);
Comment("");
//---
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
Comment("");
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
void PutOrder(int type,double price)
{
int r=0;
color clr=Green;
double sl=0,tp=0;
if(type==1 || type==3 || type==5)
{
clr=Red;
if(StopLoss>0)
sl=NormalizeDouble(price+StopLoss*Point,Digits);
if(TakeProfit>0)
tp=NormalizeDouble(price-TakeProfit*Point,Digits);
}
if(type==0 || type==2 || type==4)
{
clr=Blue;
if(StopLoss>0)
sl=NormalizeDouble(price-StopLoss*Point,Digits);
if(TakeProfit>0)
tp=NormalizeDouble(price+TakeProfit*Point,Digits);
}
r=OrderSend(NULL,type,Lot(),NormalizeDouble(price,Digits),Slip,sl,tp,"",Magic,0,clr);
return;
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
double Lot()
{
double lot=Lots;
if(Risk>0)
lot=AccountBalance()/(Risk*100);
//-----------------------------------
if(CountOrders(1)>=2 && CountOrders(1)<6)
lot=NormalizeDouble(KLot*FindLastOrderLot(1),2);
if(CountOrders(1)>=6)
lot=NormalizeDouble((KLot*0.75)*FindLastOrderLot(1),2);
if(CountOrders(0)>=2 && CountOrders(0)<6)
lot=NormalizeDouble(KLot*FindLastOrderLot(0),2);
if(CountOrders(0)>=6)
lot=NormalizeDouble((KLot*0.75)*FindLastOrderLot(0),2);
//--------------------------------
if (lot>MAXLOT) lot = MAXLOT;
if (lot<MINLOT) lot = MINLOT;
return(lot);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
void Trailing()
{
bool mod;
double all=0,count=0,sl=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()<2)
{
all+=OrderOpenPrice()*OrderLots();
count+=OrderLots();
}
}
}
}
if(count>0)
all=NormalizeDouble(all/count,_Digits);
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==OP_BUY)
{
if(Bid-all>(TrailingStop+TrailingStep)*_Point)
{
if(OrderStopLoss()<Bid-(TrailingStop+TrailingStep)*_Point)
{
sl=NormalizeDouble(Bid-TrailingStop*_Point,_Digits);
if(OrderStopLoss()!=sl)
mod=OrderModify(OrderTicket(),OrderOpenPrice(),sl,OrderTakeProfit(),0,Yellow);
}
}
}
if(OrderType()==OP_SELL)
{
if(all-Ask>(TrailingStop+TrailingStep)*_Point)
{
if((OrderStopLoss()>(Ask+(TrailingStop+TrailingStep)*_Point)) || (OrderStopLoss()==0))
{
sl=NormalizeDouble(Bid+TrailingStop*_Point,_Digits);
if(OrderStopLoss()!=sl)
mod=OrderModify(OrderTicket(),OrderOpenPrice(),sl,OrderTakeProfit(),0,Yellow);
}
}
}
}
}
}
}
//+------------------------------------------------------------------+
//| Подсчет ордеров по типу |
//+------------------------------------------------------------------+
int CountOrders(int type)
{
int count=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==type)
count++;
}
}
}
return(count);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int FindOrderType()
{
int oticket,ticketNumber=0,type=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
oticket=OrderTicket();
if(oticket>ticketNumber)
{
ticketNumber=oticket;
type=OrderType();
}
}
}
}
return(type);
}
//+------------------------------------------------------------------+
//| послекдний ордер по типу |
//+------------------------------------------------------------------+
double FindLastOrderLot(int type)
{
double OLot=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==type)
{
if(OLot<OrderLots())
OLot=OrderLots();
}
}
}
}
return(OLot);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
double FindLastBuyPrice()
{
int oticket,ticketNumber=0;
double oprice=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderType()==OP_BUY && OrderMagicNumber()==Magic)
{
oticket=OrderTicket();
if(oticket>ticketNumber)
{
ticketNumber=oticket;
oprice=OrderOpenPrice();
}
}
}
}
return(oprice);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
double FindLastSellPrice()
{
int oticket,ticketNumber=0;
double oprice=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderType()==OP_SELL && OrderMagicNumber()==Magic)
{
oticket=OrderTicket();
if(oticket>ticketNumber)
{
ticketNumber=oticket;
oprice=OrderOpenPrice();
}
}
}
}
return(oprice);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
void CloseAll(int ot=-1)
{
bool cl;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==0 && (ot==0 || ot==-1))
{
RefreshRates();
cl=OrderClose(OrderTicket(),OrderLots(),NormalizeDouble(Bid,Digits),Slip,White);
}
if(OrderType()==1 && (ot==1 || ot==-1))
{
RefreshRates();
cl=OrderClose(OrderTicket(),OrderLots(),NormalizeDouble(Ask,Digits),Slip,White);
}
}
}
}
}
//+------------------------------------------------------------------+
//| Профит всех ордеров по типу ордера |
//+------------------------------------------------------------------+
double AllProfit(int ot=-1)
{
double pr=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==0 && (ot==0 || ot==-1))
{
pr+=OrderProfit()+OrderCommission()+OrderSwap();
}
if(OrderType()==1 && (ot==1 || ot==-1))
{
pr+=OrderProfit()+OrderCommission()+OrderSwap();
}
}
}
}
return(pr);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
double Prof()
{
double pr=Profit;
pr=NormalizeDouble((AccountBalance()/100)*Profit,4);
return (pr);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int Sig()
{
int sig=3;
double up=iBands(NULL,0,BBPeriod,BBDev,0,0,1,Shift);
double dn=iBands(NULL,0,BBPeriod,BBDev,0,0,2,Shift);
double rsi2=iRSI(NULL,0,20,0,2);
double rsi1=iRSI(NULL,0,20,0,1);
bool BuyRsi=(rsi1<35);
bool SellRsi=(rsi1>65);
if(SellRsi)
{
if(Close[Shift]>up)
sig=1;
}
if(BuyRsi)
{
if(Close[Shift]<dn)
sig=0;
}
return(sig);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
void ModifyOrders()
{
double allb=0,alls=0;
double countb=0,counts=0,tp=0,sl=0;
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==0)
{
allb+=OrderOpenPrice()*OrderLots();
countb+=OrderLots();
}
if(OrderType()==1)
{
alls+=OrderOpenPrice()*OrderLots();
counts+=OrderLots();
}
}
}
}
if(countb>0)
allb=NormalizeDouble(allb/countb,Digits);
if(counts>0)
alls=NormalizeDouble(alls/counts,Digits);
for(int i=OrdersTotal()-1; i>=0; i--)
{
if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
{
if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
{
if(OrderType()==0)
{
if(TakeProfit>0)
tp=NormalizeDouble(allb+TakeProfit*Point,Digits);
if(StopLoss>0)
sl=NormalizeDouble(allb-StopLoss*Point,Digits);
if(OrderTakeProfit()!=tp || OrderStopLoss()!=sl)
bool mod=OrderModify(OrderTicket(),OrderOpenPrice(),sl,tp,0,Yellow);
}
else
if(OrderType()==1)
{
if(TakeProfit>0)
tp=NormalizeDouble(alls-TakeProfit*Point,Digits);
if(StopLoss>0)
sl=NormalizeDouble(alls+StopLoss*Point,Digits);
if(OrderTakeProfit()!=tp || OrderStopLoss()!=sl)
bool mod=OrderModify(OrderTicket(),OrderOpenPrice(),sl,tp,0,Yellow);
}
}
}
}
}
//+------------------------------------------------------------------+
//| Expert tick function |
//+------------------------------------------------------------------+
void OnTick()
{
double mn=iBands(NULL,0,BBPeriod,BBDev,0,0,0,Shift); //Main
double mn2=iBands(NULL,0,BBPeriod,BBDev,0,0,0,Shift+1); //Main
if(CloseSig>0)
{
if(Bid<mn2 && Bid>mn)
{
CloseAll(0);
}
if(Bid>mn2 && Bid<mn)
{
CloseAll(1);
}
}
if(TrailingStop>0)
{
Trailing();
}
//------------------
if(AllProfit(0)>=Prof() && Profit>0 && CountOrders(0)>1)
{
CloseAll(0);
}
if(AllProfit(1)>=Prof() && Profit>0 && CountOrders(1)>1)
{
CloseAll(1);
}
if(t!=Time[0])
{
if(CountOrders(1)<1 && Sig()==1)
{
PutOrder(1,Ask);
ModifyOrders();
}
if(CountOrders(0)<1 && Sig()==0)
{
PutOrder(0,Bid);
ModifyOrders();
}
//-------------------------------------------
if(CountOrders(0)<Count)
{
if(FindOrderType()==0 && (FindLastBuyPrice()-Ask)/_Point>=StepOrder)
{
if(Sig()==0)
{
PutOrder(0,Ask);
ModifyOrders();
}
}
}
if(CountOrders(1)<Count)
{
if(FindOrderType()==1 && (Bid-FindLastSellPrice())/_Point>=StepOrder)
{
if(Sig()==1)
{
PutOrder(1,Bid);
ModifyOrders();
}
}
}
t=Time[0];
}
Comment("\n Prof(): ",Prof());
}
Комментарии (7)
14 verta81 Автор Сообщений: 454
16 ssg Сообщений: 817
В вашем примере функция находит тикет последнего ордера, последнего закрытого и тип последней открытой.
Мне нужно найти лот последнего Buy или Sell
и потом же умножить его на кеф для следующего ордера Buy или Sell
14 verta81 Автор Сообщений: 454
16 ssg Сообщений: 817
35 AM2 Сообщений: 16425 - Андрей
sell 0.1
sell 0.1
sell 0.2
sell 0.4
buy 0.8
sell 0.16
сбой пошел же на buy, лот которого должен быть начальный 0.1
Вот ищу где ощибка
14 verta81 Автор Сообщений: 454
Нашел решение своей проблемы по примеру кода Андрея.
Благодарочка!!!
14 verta81 Автор Сообщений: 454
Зарегистрируйтесь или авторизуйтесь, чтобы оставить комментарий