Announcement

Collapse
No announcement yet.

Partner 728x90

Collapse

Whoa - how exactly does NT calculate "slippage"?

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Whoa - how exactly does NT calculate "slippage"?

    Hi guys-

    I've come across some behavior regarding slippage that I find to be somewhat troubling, and I'm interested in getting a better feel for the mechanism behind the slippage calculations in backtesting.

    As always, I'm trying to determine why real-time performance in some strategies is significantly different than backtesting. I'm highly familiar with all of the standard responses, but this one goes a little further.

    I generally try to build a lot of slippage into backtests - way more than what I would expect normally. I "assumed" that slippage was being correctly modeled, so that if I attempted "live" trading (this is really just using live data, not real money) I should get approximately similar results.

    What I'm finding instead is that - at least for stops - I do not believe Ninja calculates slippage correctly at all. Let me share an example:

    I ran a backtest on 6B going back to 8/1/2010. In the first example, I built in no slippage on execution, and came out with a final net profit in that case of $21,207. This number was based on a total of 141 trades that were stopped out @ market, 6 contracts per trade on average. For this backtest, the average profit per trade was $62.37. I used limit orders on entries and profitable exits. Only stops were market trades.

    I then ran the same backtest, except this time I incorporated 10 ticks of slippage.

    Instead of getting negative profit out of the backtest, I got $19,662. The average profit per trade had simply dropped to $57.83.

    141 trades that were stopped @ market, 6 contracts per trade, tick size of $6.25, tick slippage of 10 = $52,875 (I mean, who wouldn't want a trading system that makes 10 ticks like that per trade, guaranteed?) Yet the backtest showed a slight decline of $1,600.

    So, based on this, I'd like a little more information regarding how slippage is actually calculated - for market orders, as well as for stop-market orders.

    Kind Regards,
    CG

    PS I get the feeling that live trading (again, "live" being with live data, not real money) correctly models slippage, which is where I'm seeing the types of losses I was attempting to model in the first place.
    Last edited by cgeorgan; 04-08-2011, 06:09 AM.

    #2
    Hello,

    A couple quick questions.

    Just to clarify this is only during backtest correct?

    Secondly when you say this:

    except this time I incorporated 10 ticks of slippage.

    How specifically are you incorporating this?

    I look forward to assisting you further.

    Comment


      #3
      Originally posted by NinjaTrader_Brett View Post
      Hello,

      A couple quick questions.

      Just to clarify this is only during backtest correct?

      Secondly when you say this:

      except this time I incorporated 10 ticks of slippage.

      How specifically are you incorporating this?

      I look forward to assisting you further.
      1.)Re: Only during the backtest - I'm working on determining what sort of slippage shows up in "live" trading.

      2.)Slippage incorporated on strategy settings: Slippage = "10", I assume, means 10 ticks...hopefully, it doesn't mean 10 minimum price movements, or something to that effect.

      Comment


        #4
        Hello,

        OK thanks for that information.

        Below is the code from DefaultFillType that governs the fill of orders:

        Code:
         
        [FONT=Consolas][SIZE=2][COLOR=#008000][FONT=Consolas][SIZE=2][COLOR=#008000][FONT=Consolas][SIZE=2][COLOR=#008000]/* *** Slippage ***
        * Slippage values are optionally set in the UI and only applied to market and stop market orders
        * Slippage can only be applied to if the bar the order is filled on could have accomodated slippage
        [/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2][/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT] 
        [FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]else[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]if[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] (order.OrderType == OrderType.Stop)
        {
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#008000][FONT=Consolas][SIZE=2][COLOR=#008000][FONT=Consolas][SIZE=2][COLOR=#008000]// Stop orders are triggered when traded at the stop price
        [/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2][/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]double[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] nextLow = NextLow;
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]double[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] nextHigh = NextHigh;
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]double[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] nextOpen = NextOpen;
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]if[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] ((order.OrderAction == Cbi.OrderAction.Buy && order.StopPrice <= nextHigh + epsilon)
        || (order.OrderAction == Cbi.OrderAction.BuyToCover && order.StopPrice <= nextHigh + epsilon)
        || (order.OrderAction == Cbi.OrderAction.Sell && order.StopPrice >= nextLow - epsilon)
        || (order.OrderAction == Cbi.OrderAction.SellShort && order.StopPrice >= nextLow - epsilon))
        {
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]if[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2] (order.OrderAction == Cbi.OrderAction.Buy || order.OrderAction == Cbi.OrderAction.BuyToCover)
        FillPrice = order.StopPrice < nextOpen - epsilon ? [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Min(nextHigh, nextOpen + SlippagePoints) : [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Min(nextHigh, order.StopPrice + SlippagePoints);
        [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff][FONT=Consolas][SIZE=2][COLOR=#0000ff]else
        [/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2]FillPrice = order.StopPrice > nextOpen + epsilon ? [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Max(nextLow, nextOpen - SlippagePoints) : [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Max(nextLow, order.StopPrice - SlippagePoints);
        }
        }
        [/SIZE][/FONT][/SIZE][/FONT]
        Specifically what your interested in is this section here, which shows the code for exactly how the stop price is calculated in backtest. This can found on your PC for study at My Documents->NinjaTrader7->Bin->Custom->Type->DefaultFilllType.

        Code:
        [FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2]
        FillPrice = order.StopPrice > nextOpen + epsilon ? [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Max(nextLow, nextOpen - SlippagePoints) : [/SIZE][/FONT][/SIZE][/FONT][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af][FONT=Consolas][SIZE=2][COLOR=#2b91af]Math[/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][/COLOR][/SIZE][/FONT][FONT=Consolas][SIZE=2][FONT=Consolas][SIZE=2].Max(nextLow, order.StopPrice - SlippagePoints);
        [/SIZE][/FONT][/SIZE][/FONT]

        Comment


          #5
          Yes - I had actually gone into that bit of code and examined it myself.

          I can tell you that, based on this, you are not correctly modeling slippage. I should not be able to enter "10 ticks" of slippage, as I did in the example I gave you, and only get $1600 in losses on a total of 846 contracts sold at market (That's $2 per contract, and only 1/3 of the minimum tick movement). I entered 20 ticks of slippage, and got a similarly anemic result for slippage.

          I think you guys need to go back and re-code this. Run the numbers yourself - take any system, look at the number of market trades and number of contracts (you guys know how to do this simply by exporting "trades" data to excel and summing up), and multiply by tick size and slippage amount. It's all incorrect.

          PS The error appears to be in "slippage points". If you're simply taking the number from the strategy settings (I.e. "10"), that's incorrect. This number needs to be multiplied by the minimum tick size and adjusted by the price multiple for effective conversion.

          EDIT - I can also see you do a min/max calculation based on nextHigh and nextLow - theoretically nobody should be able to get stopped out (or filled) at higher prices than what was seen. However, for modeling purposes, the user should be allowed to actually specify greater slippage than what "historically" occurred.
          Last edited by cgeorgan; 04-08-2011, 07:52 AM.

          Comment


            #6
            Hello,

            Thanks for the recount.

            SlippagePoints is already adjusted for tick value for use.

            I will look into the fill model here later today and see if theres anything that can be done. However more then likely it is like this due to reasons we have found in the past and is as close as we can get it to live market conditions in a backtest environment. As you know we have to run off bar point prices which can cause these descrepencies between historical vs backtest.




            Comment


              #7
              Hello,

              Looked into. See no issue with logic as is.

              Slippage will be added to the fill price of the order up to the low of the bar vice versa.

              So if you had an order to exit a long at 1000 and the low of the bar was 995 and your using 10 ticks of slippage.

              You would be filled at the Maximum value of with low of the bar 995 even though you had 10 ticks in slippage inputed. Since it was not possible in market conditions to give you more slippage on this bar your stop price in this example would be 995. Not 990 with your 10 ticks of slippage. This more closely resembles market conditions.

              Let me know if I can be of further assistance.

              Comment


                #8
                Originally posted by NinjaTrader_Brett View Post
                Hello,

                Looked into. See no issue with logic as is.

                --

                Since it was not possible in market conditions to give you more slippage on this bar your stop price in this example would be 995. Not 990 with your 10 ticks of slippage. This more closely resembles market conditions.

                --

                Let me know if I can be of further assistance.
                That's true, if you're only trying to model small amount (1-2 contracts, or any amount really that's within the bid/ask sizes).

                What if, on the other hand, I'm trying to model 50 contracts of RBOB gasoline against a bid/ask size of 5-6 contracts? In this case, I'd like to build into my model an assume 5-10 points of slippage.

                Regardless, I do think (this is just my opinion) that user-desired slippage settings should override anything that the program "thinks" can be done. Perhaps something to pass on to your developers?

                Comment


                  #9
                  Hello,

                  This is something coded specifically in. As then if we allowed this we would get support reports from customers wondering why they got a fill lower or higher then the bar.

                  However in your case this is the reason we have the fill type open and allowable for you to edit. There are differing opinions on how it should work in backtest.

                  I would suggest you simply go in and remove the Math.Max and Math.Min call so that it will always calculated slippage in and does not cap it out at the low or high of the bar. This way you can get exactly what you like.

                  Let me know if I can be of further assistance.

                  Comment


                    #10
                    I guess...Re: Customers that complain about having added features - do you really need these sorts of customers?

                    No need to answer that. Just being rhetorical.

                    I'll go ahead and edit the code on my own - Thank you for the pointers.

                    Comment


                      #11
                      Thanks. No problem glad to show you where to edit to get your specific functionality needed.

                      Comment

                      Latest Posts

                      Collapse

                      Topics Statistics Last Post
                      Started by love2code2trade, 04-17-2024, 01:45 PM
                      4 responses
                      31 views
                      0 likes
                      Last Post love2code2trade  
                      Started by cls71, Today, 04:45 AM
                      2 responses
                      10 views
                      0 likes
                      Last Post eDanny
                      by eDanny
                       
                      Started by proptrade13, Today, 11:06 AM
                      0 responses
                      4 views
                      0 likes
                      Last Post proptrade13  
                      Started by kulwinder73, Today, 10:31 AM
                      1 response
                      10 views
                      0 likes
                      Last Post NinjaTrader_Erick  
                      Started by RookieTrader, Today, 09:37 AM
                      3 responses
                      15 views
                      0 likes
                      Last Post NinjaTrader_ChelseaB  
                      Working...
                      X