optimize (var start, var min, var max, var step, var bias) : var

Optimizes a strategy parameter for the current asset and algo. In [Test] or [Trade] mode, this function returns either the previously optimized parameter value, or - if the PARAMETERS mode is not set - it just returns start. In [Train] mode the function attempts to find the best parameter value between min and max.

For this the simulation runs through many cycles. For every cycle the optimize function generates a different value between min and max. At the end of each cycle, the number of winning trades (bright blue bars below), losing trades (dark blue) and the parameter's performance (red) are plotted in a chart. The best parameter value is then selected and internally stored.

The chart above is a typical result of an optimize call in [Train] mode. The strategy parameter to be optimized here is used for a buy/sell threshold. It varies from 0.200 to 3.00 in constant steps of 0.1. We have a small performance peak around 0.90 and the highest peak at 1.60. The best parameter value however is 1.70, with a performance of 2.7 and 125 winning trades. Although its adjacent bars are higher, the optimizer selects the center of the broad peak that represents not the most profitable, but the most robust parameter value. Using the value of a very narrow peak or of a single line bears the danger of overfitting the strategy. Once the best parameter value is determined, the optimization process continues for the next parameters.

By using several optimize calls in the code, any number of parameters can be optimized at the same time. The more parameters are optimized, the more often the script must be run, and the longer will it take. The best value of one parameter is automatically used for optimizing the next parameters. At the end of a multi parameter optimization, the best parameters are displayed in the message window in the order of their optimize calls, and they are stored in the parameter file belonging to the strategy. This file is automatically loaded when the PARAMETERS mode is set.

If the script trades multiple assets or algorithms and contains loop calls, a separate parameter set for each loop is optimized.

The parameter values are stored in a text file in Data\scriptname.par. The file can be opened and examined with the script editor. Each line begins with the asset name and (if any) algorithm identifier of the parameter set. The values are listed in the order of the optimize calls in the script. A '+' before a parameter value indicates that the best value is at the end of its parameter range, so it could make sense to modify the range for better results. .

Parameters:

start Default value of the parameter, returned when the PARAMETERS mode is not set in [Test] or [Trade] mode. This should be the estimated best value of the parameter, normally in the middle of its range. Must be >= 0.
min, max Parameter range, given by its minimum and maximum values (>= 0).
step Optional step width. When 0 or omitted, 10% is added to the parameter for every optimization step. When a positive step value is given, add this constant value every step; when a negative step value is given, add its magnitude as a percentage every step (f.i. -20 adds 20% per step). Adding a percentage instead of a constant value gives a better step resolution at the begin of the range. For best results, select the step value so that every parameter has about 10..30 optimization steps. The maximum number of steps (MAX_STEPS) is defined in trading.h.
bias Optional preference of low or high parameter values. When 0 or omitted, select the optimal parameter. When > 0, prefer higher parameter values even when their rank is lower by the given bias in percent. When < 0, prefer lower parmeter values even when their rank is lower by abs(bias) in percent. Preferring values from the low or high range can make sense f.i. for setting a Stop as tight as possible even when its value is not optimal.

Returns

Current, default, or optimized parameter value, depending on training or test mode.   
 

Optimize

Predefined variable for setting up the optimization method; affects the way parameters are generated by the optimize function.

Range:

The following flags can be set or combined with '+' or '|':
TRADES Optimize considering the trade size (Lots). Large trades get more weight. Otherwise trade sizes are ignored in the training process.
PHANTOM Optimize ignoring phantom trades. Otherwise phantom trades are just normal trades in the training process.
PEAK Look for peaks in the parameter space, rather than hills.

Type:

int

 

Remarks:

Examples:

// trend trading with Moving Averages and optimized parameters
function run()
{
  set(PARAMETERS);
  Optimize = PEAK;
  var TimeCycle = optimize(30,10,100,5);  
  var TimeFactor = optimize(3,1,5);
// allow 3% tolerance for preferring low stop distances Stop = ATR(10) * optimize(3,1,10,0.5,-3); // for optimizing time periods, set the LookBack variable to the // maximum possible value (here, TimeCycle 100 * TimeFactor 5) LookBack = 100*5;
vars Price = series(price(0)); vars MA1 = series(SMA(Price,TimeCycle)); vars MA2 = series(SMA(Price,TimeCycle*TimeFactor)); plot("MA1",*MA1,0,BLUE); plot("MA2",*MA2,0,BLUE); if(crossOver(MA1,MA2)) enterLong(); else if(crossUnder(MA1,MA2)) enterShort(); }
// brute force optimization
function run()
{
  set(PARAMETERS);
  int PeriodsEMA1[4] = { 5, 10, 15, 20 };
  int PeriodsEMA2[3] = { 100, 150, 200 };
  LookBack = 250;

  int Index = optimize(1,1,4*3,1) - 1;
  int PeriodEMA1 = PeriodsEMA1[Index%4];
  int PeriodEMA2 = PeriodsEMA2[Index/4];
  
  vars Price = series(price(0));
  vars EMA1 = series(EMA(Price,PeriodEMA1));
  vars EMA2 = series(EMA(Price,PeriodEMA2));
  
  if(crossOver(EMA1,EMA2))
    enterLong();
  else if(crossUnder(EMA1,EMA2))
    enterShort();
}
// alternative objective function based on Calmar ratio
var objective()
{
	return(ThisPerformance.vWin-ThisPerformance.vLoss)/max(1,ThisPerformance.vDrawDown);
}

// alternative objective function based on Sharpe ratio
var objective()
{
	if(!NumWinTotal && !NumLossTotal) return 0.;
	return ThisPerformance.vMean/ThisPerformance.vStdDev;
}

// alternative objective function for binary options
var objective()
{
	return ((var)(NumWinLong+NumWinShort))/max(1,NumLossLong+NumLossShort);
}

See also:

Training, loop, NumParameters, NumOptCycles, Workshop 5, user supplied functions

► latest version online