Optimisation - Is it a fallacy?

 
Hi,

I'm curious to chat to anyone who has been seriously attempting to optimise their trading systems and very interested to know the sort of results they've managed to get. Personally, I'm beginning to wonder if optimisation is a bit of a fallacy?

The reason I'm suggesting this is as follows. I've been developing trading systems for a while now and was initially a great believer in optimisation. So, I bought plenty of data and got on with experimenting. My method is as follows:

1. I have 8 years of M5 data for each currency pair. I use the first 7 years for the actual optimisation process and the last year for forward testing.

2. I have created numerous trading systems that when optimised, return between 30 - 50% per year over the optimisation period. That means a total theoretical return of between 210 - 350% for the 7 year period. That 30% - 50% yearly return is a fairly linear return over that time period - i.e. the drawdown wouldn't be much more than 10% of the initial trading capital.

3. Approximately 2000-2500 trades take place over this 7 year optimisation period. I would have thought that this number of trades would have been statistically significant in a positive sense.

However, when I then run this optimised trading system on the last year of data (i.e. forward test the trading system), I'm lucky to break even. And this seems to happen EVERY TIME, with all sorts of different trading strategies!

Is there anyone out there who has managed to consistently achieve good, forward testing results after optimising a trading system? I know that decreasing the number of variables should decrease the chance of over-optimisation - I've been down that road. Anyone got any ideas/comments?
 
I advise you to esteem this book - Long-Term Secrets to Short-Term Trading by Larry Williams - http://www.amazon.com/Long-Term-Secrets-Short-Term-Trading-Williams/dp/0471297224/ref=pd_bbs_sr_1/002-6991764-2478422?ie=UTF8&s=books&qid=1174975733&sr=8-1

And also this book is very useful - Fooled by Randomness: The Hidden Role of Chance in Life and in the Markets by Nassim Nicholas Taleb - http://www.amazon.com/Fooled-Randomness-Hidden-Chance-Markets/dp/0812975219/ref=pd_bbs_2/002-6991764-2478422?ie=UTF8&s=books&qid=1174975923&sr=1-2
 
Thanks Rosh, for the links to the two books. I've ordered "Fooled by Randomness: The Hidden Role of Chance in Life and in the Markets" but the reviews on the other one you recommended weren't that good unfortunately, so I'll try and get that one from the library...

But I (probably like lots of other people) have started to wonder whether the whole idea of building trading systems based on historical data is all a bit of a fallacy. Are the markets then actually random? One would instinctively say not when you start playing with trend lines etc but apart from that, all the usual technical analysis tools, chart patterns etc seem to deliver signals which pretty much work out to a 50/50 chance over the long term - from my experience anyway. This seems to be the case whether you talk about indicators, chart patterns etc or any form of TA, apart from trendlines. Is there anyone out there who is actually trading using purely technical analysis and has consistently made good profits over a long period of time?

So, is technical analysis then a total waste of time? Are automated trading systems a total waste of time? In fact is any form of prediction going to produce consistent, long term profits?

Ah, I hear you say - the trading competition! People made good money with their Experts. But is this also a fallacy? Could it maybe be the case that the market conditions were such that those experts that did well just happened to have the relevant signals in them that made them profitable for that particular period of time? i.e. if the market conditions had been different over that three month period, would a completely different set of Experts have "won"? The winner of the trading competition (Rich) wouldn't have traded his Expert in real-time because it had a 92% drawdown. How would that Expert have performed over 2-3 years? I think I've pretty much proven to myself that even using 7 years of historical data doesn't produce trading systems that are profitable in the future, unless a great deal of luck is involved.

If anyone reading this feels they would like to contribute to this thread, by all means, please do. I think it'd be good to get a frank discussion going as to whether anybody out there is actually doing well using purely technical analysis.
 
I understand your concerns, but each is responsible for these issues. I gave you a reference to the book in order to show you the financial markets with the right perspective. Patterns in the market there, and people are trying to trade speculation, but not always, these patterns can be detected. Often people develop complex trading strategies with many parameters, while profitable system should be as simple as possible. I might even give a reference to the book, which is very useful, but making code Expert Adviser.
//+------------------------------------------------------------------+
//|                                                        kotov.mq4 |
//|                                                             Rosh |
//|                 http://forum.viac.ru/viewtopic.php?p=68234#68234 |
//+------------------------------------------------------------------+
#property copyright "Rosh"
#property link      "http://forum.viac.ru/viewtopic.php?p=68234#68234"
//---- input parameters
extern int       CloseHour=14;
extern int       Slippage=3;
extern double    SpreadK=2.0;
extern double    Lots=0.1;
extern int       PeriodType=0; // если нол? - идем 4-х часвокам, если не нол? - по дневкам
extern double    StopLoss;
extern int       ExpertMagicNumber=3002;
extern double    Zazor=5; // отступ от экстемума предыду?его бара в пунктах для стопа
extern int       TrailingStop=10;
extern int       TrailingPeriodType=1;// по умолчанию(если равно нулю) по 4-часовкам трейлим
extern int       TrailingModeType=1;// по умолчанию простой трейлинг(еслиравно нулю), иначе по хаям/лоям баров
int PeriodBars;
int Spread, CurDay;
int myBars;
//+------------------------------------------------------------------+
//| expert initialization function                                   |
//+------------------------------------------------------------------+
int init()
  {
//---- 
  if (PeriodType==0) PeriodBars=PERIOD_H4; else PeriodBars=PERIOD_D1;
  if (TrailingPeriodType==0) TrailingPeriodType=PERIOD_H4; else TrailingPeriodType=0;// бары родного тайм-фрейма 
  Spread=MarketInfo(Symbol(),MODE_SPREAD);
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| expert deinitialization function                                 |
//+------------------------------------------------------------------+
int deinit()
   {
   if (IsTesting()&&!IsOptimization())
      {
      //WriteLastAccountInfo();
      //Print("Запишем статистику");
      //HistoryCalculate();
      // вывод в файл результатов бектеста
      }
   else Print("Работа эксперта на счету #",AccountNumber(), " завершена ",TimeToStr(TimeCurrent()));   
   }
//+------------------------------------------------------------------+
//| посчитаем количество открытых ордеров                            |
//+------------------------------------------------------------------+
int TotalExpert()
   {
   int total,totalExpert;
   total=OrdersTotal();
   totalExpert=0;
   if (OrdersTotal()>0)
      {
      for (int cnt=0;cnt<total;cnt++)
         {
         OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES);
         if ((OrderMagicNumber()==ExpertMagicNumber)&&(Symbol()==OrderSymbol())) 
            {
            totalExpert++;
            }
         }
      }
   return(totalExpert);      
   }
//+------------------------------------------------------------------+
//| признак появления нового бара                                    |
//+------------------------------------------------------------------+
bool isNewBar()
   {
   bool res=false;
   if (myBars!=Bars)
      {
      myBars=Bars;
      res=true;
      }
   return(res);   
   }
//+------------------------------------------------------------------+
//| закрытие ордеров                                                 |
//+------------------------------------------------------------------+
void CloseAllOrders()
  {
   int typeTrade;
//---- 
   for (int cnt=OrdersTotal()-1;cnt>=0;cnt--)
      {
      OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES);
      if (OrderMagicNumber()!=ExpertMagicNumber) continue;
      if (OrderSymbol()!=Symbol()) continue;
      typeTrade=OrderType();
      //Print("typeTrade=",typeTrade);
      switch (typeTrade)
         {
         case OP_BUY: {OrderClose(OrderTicket(),OrderLots(),Bid,Slippage,Yellow);Sleep(30000);break;}
         case OP_SELL:{OrderClose(OrderTicket(),OrderLots(),Ask,Slippage,Yellow);Sleep(30000);break;}
         default: break;
         }
      }
   return(0);
  }
//+------------------------------------------------------------------+
//| трейлинг ордеров                                                 |
//+------------------------------------------------------------------+
void TrailingAllTrades()
  {
   int typeTrade,cnt;
//---- 
   if (TrailingModeType==0)
      {
      //============================================================      
      for (cnt=OrdersTotal()-1;cnt>=0;cnt--)
         {
         if(OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES))
            {
            if (OrderMagicNumber()!=ExpertMagicNumber) continue;
            if (OrderSymbol()!=Symbol()) continue;
            typeTrade=OrderType();
            //Print("Trailing typeTrade=",typeTrade);
            switch (typeTrade)
               {
               //case OP_BUY: 
               case OP_SELL: 
                  if (Ask-OrderOpenPrice()>TrailingStop*Point || Ask-OrderTakeProfit()>TrailingStop*Point)
                     OrderModify(OrderTicket(),OrderOpenPrice(),OrderStopLoss(),Ask-TrailingStop*Point,0,Yellow);
                  break;
               //case OP_SELL:
               case OP_BUY: 
                  if (OrderOpenPrice()-Bid>TrailingStop*Point || OrderTakeProfit()-Bid>TrailingStop*Point)
                     OrderModify(OrderTicket(),OrderOpenPrice(),OrderStopLoss(),Bid+TrailingStop*Point,0,Yellow);
                  break;
               default: break;
               }
            }
         }
      //============================================================
      }
      
   if (TrailingModeType!=0)
      {
      for (cnt=OrdersTotal()-1;cnt>=0;cnt--)
         {
         if(OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES))
            {
            if (OrderMagicNumber()!=ExpertMagicNumber) continue;
            if (OrderSymbol()!=Symbol()) continue;
            typeTrade=OrderType();
            switch (typeTrade)
               {
               //case OP_BUY: 
               case OP_SELL:
                  if ((Ask-iLow(NULL,TrailingPeriodType,1)+Zazor*Point>TrailingStop*Point)||(iLow(NULL,TrailingPeriodType,1)-Zazor*Point-OrderTakeProfit()>Point))
                     Print("TrailingModeType=",TrailingModeType,"трейлинг продаж Ask=",Ask," TrailingPeriodType=",TrailingPeriodType);
                     Print("OrderTakeProfit=",OrderTakeProfit());
                     Print("Ask-iLow(NULL,TrailingPeriodType,1)+Zazor*Point=",(Ask-iLow(NULL,TrailingPeriodType,1)+Zazor*Point)/Point);
                     Print("iLow(NULL,TrailingPeriodType,1)-Zazor*Point-OrderTakeProfit()=",(iLow(NULL,TrailingPeriodType,1)-Zazor*Point-OrderTakeProfit())/Point);

                     OrderModify(OrderTicket(),OrderOpenPrice(),OrderStopLoss(),iLow(NULL,TrailingPeriodType,1)-Zazor*Point,0,Yellow);
                  break;
               //case OP_SELL:
               case OP_BUY: 
                  if ((iHigh(NULL,TrailingPeriodType,1)+(Spread+Zazor)*Point-Bid>TrailingStop*Point)||
                     ((OrderTakeProfit()-iHigh(NULL,TrailingPeriodType,1)-(Spread+Zazor)*Point>Point)&&(OrderTakeProfit()!=0))||(OrderTakeProfit()==0))
                     //Print("TrailingModeType=",TrailingModeType,"трейлинг покупок Bid=",Bid," TrailingPeriodType=",TrailingPeriodType);
                     //Print("OrderTakeProfit=",OrderTakeProfit());
                     //Print("iHigh(NULL,TrailingPeriodType,1)+(Spread+Zazor)*Point-Bid=",(iHigh(NULL,TrailingPeriodType,1)+(Spread+Zazor)*Point-Bid)/Point);
                     //Print("OrderTakeProfit()-iHigh(NULL,TrailingPeriodType,1)-(Spread+Zazor)*Point=",(OrderTakeProfit()-iHigh(NULL,TrailingPeriodType,1)-(Spread+Zazor)*Point)/Point);

                     OrderModify(OrderTicket(),OrderOpenPrice(),OrderStopLoss(),iHigh(NULL,TrailingPeriodType,1)+(Spread+Zazor)*Point,0,Yellow);
                  break;   
               default: break;
               }
            }      
         }

      }
      
            
   return(0);
  }
//+------------------------------------------------------------------+
//| expert start function                                            |
//+------------------------------------------------------------------+
int start()
  {
  int total;
   if(!isNewBar()) return;
   
   if(IsTesting())
      {
      //GlobalVariableSet("h4time",iTime(Symbol(),PERIOD_H4,0));
      //SetTrace();
      //WriteAccountInfo();
      }
   total=TotalExpert();
//---- 
   //Print("CurTime()=",TimeHour(CurTime()));
   if (total==0 && TimeHour(CurTime())>=0 && TimeHour(CurTime())< CloseHour)
      {
      if ((Ask+Bid)/2.0>(iHigh(NULL,PeriodBars,1)+iLow(NULL,PeriodBars,1)+iOpen(NULL,PeriodBars,1)+iClose(NULL,PeriodBars,1))/4.0 && Bid>iOpen(NULL,PeriodBars,0))
         {
         if (  TimeDay( CurTime())!=CurDay   )
            {
            //OrderSend(Symbol(),OP_BUYSTOP,Lots,Ask+2*Spread*Point,Slippage,iLow(NULL,PeriodBars,1)-Zazor*Point,0,"buy",0,CurTime()+8*60*60,Blue);
            OrderSend(Symbol(),OP_SELLLIMIT,Lots,Ask+SpreadK*Spread*Point,Slippage,0,iLow(NULL,PeriodBars,1)-Zazor*Point,"selllimit",ExpertMagicNumber,CurTime()+8*60*60,Red);
            CurDay=TimeDay(CurTime());
            }
         }
      if ((Ask+Bid)/2.0<(iHigh(NULL,PeriodBars,1)+iLow(NULL,PeriodBars,1)+iOpen(NULL,PeriodBars,1)+iClose(NULL,PeriodBars,1))/4.0 && Bid<iOpen(NULL,PeriodBars,0)) 
         {
         if (  TimeDay( CurTime())!=CurDay   )
            {
            //OrderSend(Symbol(),OP_SELLSTOP,Lots,Bid-2*Spread*Point,Slippage,iHigh(NULL,PeriodBars,1)+(Ask-Bid)+Zazor*Point,0,"sell",0,CurTime()+8*60*60,Red);
            OrderSend(Symbol(),OP_BUYLIMIT,Lots,Bid-SpreadK*Spread*Point,Slippage,0,iHigh(NULL,PeriodBars,1)+(Ask-Bid)+Zazor*Point,"buylimit",ExpertMagicNumber,CurTime()+8*60*60,Blue);
            CurDay=TimeDay(CurTime());
            }
         }
      }
   if (total>0 && TimeHour(CurTime())>=CloseHour) CloseAllOrders();
      else
         {
         if (total>0 &&TrailingStop!=0)
            TrailingAllTrades();
         } 
//----
   return(0);
  }
//+------------------------------------------------------------------+



EURUSD H1

 
Hi Rosh,

Thanks again for your comments - I appreciate them. From my own experiences, it does appear to be the simple trading systems that have the most chance of success - the more parameters, the more curve fitting occurs (apparently). I remember several years ago that neural networks were all the rage but they apparently went out of vogue again after continual curve fitting problems.

Anyway, thanks for the Expert code - interesting. But I see you have the same problems as me in that your Expert only breaks even? I'm finding that it produces profits when only EURUSD 1hour data is used but if each of those 1 hour bars is interpolated with EURUSD M5 data, the Expert breaks even on my system.... Presume you're getting the same results?
 
You're welcome ;)

 
Hi Rosh,

I get similar results when I use my 1 Hour data. However, when carrying out the simulation, the Expert breaks even (i.e. makes no profit or loss) at the point where my M15 and M5 data sets start - i.e. when true interpolation begins, rather than simulated. Are you sure you've got either M15 or M5 data loaded for the entire period between 1999 - 2007?

See my graph below. The point where is profit line starts to level off is the point where my M15 and M5 data sets start...



 
You may use this forum for picture's inserting - "MQL4: Pictures for metaquotes.net forum"
 
I downloaded historical rates from History Center . There are one-minute historical bases on each major currency pair.


 
Hi Rosh,

Well, that's an interesting one - I confirmed your results when I used the MetaQuotes data you've got but when I try to run the expert on data provided by FXDD, I get the results shown above...

But congrats on creating an Expert that actually appears to be profitable long term! There does seem to be life after death!
Reason: