Intraday / Multi-Time Frame | Keep from holding positions overnight

Modified on 2010/09/12 17:24 by Eugene — Categorized as: Knowledge Base

General

For backtesting purposes, to add the condition for exiting the position at the end of the day you do the following in a single position strategy:

if( IsLastPositionActive ) { // exit on the last bar of the day if( Bars.IsLastBarOfDay(bar) ) ExitAtClose( bar, LastPosition, "Last Bar" ); }

Or in a multiple open positions strategy that translates to:

for(int p = ActivePositions.Count - 1; p >= 0; p--) { Position pos = ActivePositionsp; // exit on the last bar of the day if( Bars.IsLastBarOfDay(bar) ) ExitAtClose( bar, pos, "Last Bar" ); }

However, sometimes it gets more tricky. Read on below:

Problem



I'm trying to code an intraday strategy that doesn't hold any positions overnight. In order to do this I need to keep the buy limit order from being placed on the bar before the last bar of the day, since if the order gets executed, I can't get out of it on the next bar. I'm using WL6 with autotrading so I can't use SellAtClose orders (not supported).

Code

The slider for "Today Close" allows a convenient switch to adjust for a short day's close at 1pm.

using System; using System.Collections.Generic; using System.Text; using System.Drawing; using WealthLab; using WealthLab.Indicators;

namespace WealthLab.Strategies { public class MOCStrategy : WealthScript { /* Returns 24-hour time as an integer * Example: 4pm = 1600 */ public int GetTime(int bar) { return Datebar.Hour * 100 + Datebar.Minute; } /* Adds minutes to an integer time (HHnn) and returns a HHnn time * Example 1600 - 5 = 1555 */ public int AddIntegerTime( int t, int minutes ) { int res = 60 * ( t / 100 ) + ( t % 100 ); // minutes past midnight int res1 = res + minutes; res1 = res1 / 60 * 100 + ( res1 % 60 ); if( res1 >= 2400 ) return (res1 % 2400 ); else if( res1 < 0 ) return AddIntegerTime( AddIntegerTime( 2400, minutes ), res ); else return res1; } /* Returns the chart bar number of the first bar of the startDay. * Example: Pass 2 to get the first bar of the second day */ public int FirstBarofDay( int startDay ) { int cnt = 0; for (int Bar = 0; Bar < Bars.Count; Bar++) { if( Bars.IntradayBarNumber( Bar ) == 0 ) cnt++; if( cnt == startDay ) return Bar; } return Bars.Count; } /* Sliders * minTradeBars are the min number of bars before the end of day that an entry is allowed */ private StrategyParameter todayCloseTime; private StrategyParameter minTradeBars; public MOCStrategy() { todayCloseTime = CreateParameter("Close Today", 1600, 1300, 1600, 300); minTradeBars = CreateParameter("Min Trade Bars", 5, 2, 10, 1); } protected override void Execute() { int todayClose = todayCloseTime.ValueInt; int minBarsInTrade = minTradeBars.ValueInt; int lastChartBar = Bars.Count - 1; int nextToLastBarTime = AddIntegerTime( todayClose, -Bars.BarInterval ); for(int bar = FirstBarofDay( 2 ); bar < Bars.Count - 1; bar++) { if( !IsLastPositionActive ) { if ( bar < lastChartBar - minBarsInTrade ) { BuyAtLimit(bar + 1, Bars.Lowbar * 0.995); } } else { Position p = LastPosition; if( (bar == lastChartBar) && (GetTime(bar) >= nextToLastBarTime) ) { SetBarColor( bar, Color.Orange); ExitAtMarket( bar + 1, p, "Exit at open of last bar"); } else if ( (bar != lastChartBar) && Bars.IsLastBarOfDay(bar + 1) ) { SetBarColor( bar, Color.Orange); ExitAtMarket( bar + 1, p, "Exit at open of last bar"); } else { // other exit logic here } } } } } }