Introduction:
This is a very simple channel breakout trading system. It does not utilize bollinger bands to detect a breakout condition, but rather a threshold based on the maximum and minimum values of the last X candles. If the threshold is exceeded by the current candle, a trade is placed in the direction of the breakout. Once a trade is entered, a trailing stop with a fixed value takes us out.
Rules:
The rules of the trading system are the following:
Run Results:
The system was optimized with the tick file shipped with the compiled version of the software and the following parameters:
MINUTES:5;CHANNEL:10-30;TRAILSTOP:0.0003-0.0020,0.0001;LOG:3
The end of run summary results are listed at the end of this post.
As you can see, the optimization captured a fundamental characteristic unique to this file that results in profitability when the system uses a channel length greater than 25 and a trailing stop of 17 or 19 pips. I do not like the fact that a stop of 18 pips does not result in profitable trades.
For the system to exhibit robustness, a channel length of greater than 25 and a traling stop of between 17 and 19 pips would have to result in profitability.
These are encouraging results, but more optimization runs need to be conducted with other tick files.
You can download the compiled program, or create an account to download the source code
Program Output:
...
_4XLab.NET.fXChannelBreakout EndedAnalyzing Run Results----------------------Profitable Parameters:MINUTES:5;CHANNEL:16;TRAILSTOP:0.002;MINUTES:5;CHANNEL:21;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:22;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:25;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:25;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:26;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:26;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:27;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:27;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:28;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:28;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:29;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:29;TRAILSTOP:0.0019;MINUTES:5;CHANNEL:30;TRAILSTOP:0.0017;MINUTES:5;CHANNEL:30;TRAILSTOP:0.0019;--------------------------------------------------For Maximum Margin Gain:Tick Source: E:\MyDocs\Visual Studio Projects\4XLab.NET\bin\Debug\EUR_USD_Jan_2006_Week1_Small.csvParameters Sent: MINUTES:5;CHANNEL:29;TRAILSTOP:0.0019;LOG:3; AMG:1000;ALV:50;AAL:0.3;LOG:3;ACOC:0.03;AAPI:600;Parameters Reported By Transform:MINUTES:5;CHANNEL:29;TRAILSTOP:0.0019;Margin Stats: O:1000.00, H:1035.80, L:975.84, C:1010.27 Drawdown:-36.78PIP Stats: Pips Captured:0.00100, H:0.00300, L:-0.00190 Drawdown:-0.00290Volume moved on account:22138.48Orders Placed:30Winning Trades:8Maximum Winning Streak:4Losing Trades:7Maximum Losing Streak:2Maximum Gain:0.00380Maximum Loss:-0.00190Minimum Gain:0.00020Minimum Loss:-0.00040Average Gain:0.00116Average Loss:-0.00119Total Gain:0.00930Total Loss:-0.00830--------------------------------------------------------For Minimum Drawdown:Tick Source: E:\MyDocs\Visual Studio Projects\4XLab.NET\bin\Debug\EUR_USD_Jan_2006_Week1_Small.csvParameters Sent: MINUTES:5;CHANNEL:25;TRAILSTOP:0.0017;LOG:3; AMG:1000;ALV:50;AAL:0.3;LOG:3;ACOC:0.03;AAPI:600;Parameters Reported By Transform:MINUTES:5;CHANNEL:25;TRAILSTOP:0.0017;Margin Stats: O:1000.00, H:1020.61, L:973.54, C:1000.45 Drawdown:-31.51PIP Stats: Pips Captured:0.00020, H:0.00180, L:-0.00210 Drawdown:-0.00250Volume moved on account:22377.94Orders Placed:34Winning Trades:8Maximum Winning Streak:3Losing Trades:9Maximum Losing Streak:2Maximum Gain:0.00240Maximum Loss:-0.00170Minimum Gain:0.00040Minimum Loss:-0.00020Average Gain:0.00114Average Loss:-0.00099Total Gain:0.00910Total Loss:-0.00890----------------------------System Tester Ended
//// 4X Lab.NET © Copyright 2005-2006 ASCSE LLC// http://www.4xlab.net// email: 4xlab@4xlab.net//using System;namespace _4XLab.NET{ public class fXChannelBreakout : ForexObject { int Minutes; int channel; double trailstop; iMinMax minmax; sCandle Candle; double spread; cCandleBuilder cbx;
public override void Init(string pParameters) { this.InitializeParameters(pParameters,"MINUTES:5;CHANNEL:25;TRAILSTOP:0.0010;"); Minutes = (int)PParser.GetDouble("MINUTES",0); channel = (int)PParser.GetDouble("CHANNEL",0); trailstop = PParser.GetDouble("TRAILSTOP",0); minmax = new iMinMax(2*channel); cbx = new cCandleBuilder(Minutes,10); Framework.TickServer.RegisterTickListener("cbx","*",cbx); cbx.RegisterCandleListener("cbx",this); Framework.TickServer.RegisterTickListener("System","*",this); Framework.WriteGraphLine("InTrade,Margin,C"); }
public override void ReceiveTick(sTick pTick) { spread = pTick.Ask - pTick.Bid; }
public override void ReceiveCandle(sCandle pCandle, int pPeriod, string pCBTitle) { if ((pPeriod==Minutes) && (pCBTitle=="cbx")) { Candle = pCandle; if (minmax.isPrimed()) { DecisionFunction(); } // do not include current candle in Min/Max data // until after the decision function minmax.ReceiveTick(Candle.H); minmax.ReceiveTick(Candle.L); } } private void DecisionFunction() { switch (Framework.Account.InTrade()) { case 0: { if (Framework.Account.InTrade()==0) { if (EntryCriteriaLong()) { Framework.Account.EnterTrade(1); Framework.Account.SetTrailingStop(trailstop); } } if (Framework.Account.InTrade()==0) { if (EntryCriteriaShort()) { Framework.Account.EnterTrade(-1); Framework.Account.SetTrailingStop(trailstop); } } break; }
case 1: { if (ExitCriteriaLong()) { //Framework.Account.ExitTrade(); } break; }
case -1: { if (ExitCriteriaShort()) { //Framework.Account.ExitTrade(); } break; } }
double logInTrade = Framework.Account.InTrade(); double logMargin = Framework.Account.GetAccount().C; //Framework.WriteGraphLine("InTrade,Margin,C"); Framework.WriteGraphLine(logInTrade+","+logMargin+","+Candle.C); }
private bool EntryCriteriaLong() { bool v = false; if (Candle.C > minmax.Max()) { v = true; } return v; }
private bool EntryCriteriaShort() { bool v = false; if (Candle.C < minmax.Min()) { v = true; } return v; }
private bool ExitCriteriaLong() { bool v = false; if (v) { v = true; } return v; }
private bool ExitCriteriaShort() { bool v = false; if (v) { v = true; } return v; }
public override bool Finished() { bool returnv = true; return returnv; }
public override string Title() { return "X Length Channel Breakout"; }
}}