-
Notifications
You must be signed in to change notification settings - Fork 255
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
How to simulate proper stop trailing in T+1 market? #41
Comments
Hi @none2003, I've committed a change so that stops are checked before any scheduled orders are placed. It should fix your issue. Let me know! |
Hi @edtechre, I tried, it works, thank you! With that, I have a question. If I set a trailing stop at 2% (ctx.stop_trailing_pct = 2), and if the stock falls more than 2% the same day after I buy it, and opens lower the next day, and falls throughout the day, there is no way to guarantee that the stop trailing is only at 2%, right? Because I can see in the "return_pct" column of result trades, the maximum stop loss range is -2, so I have this question. |
The stop will be filled at the stop threshold, which in your case would be 2% from the entry. If you want to simulate a different fill, you need to code a trailing stop yourself with a custom sell_fill_price like in #25. |
Maybe I didn't make myself clear. If the stock price fell more than 2% on the day it was bought and continued to fall the next day, but the trade will only fill the next day, how can the "return_pct" be just -2%? |
The execution is as follows:
The previous behavior was checking stops on Day 2, which allowed for stops to be triggered on the same bar an entry was opened. But this was your original issue. If you need the return_pct to be less than -2% percent, you will need to code the stop rules yourself and set the desired sell_fill_price when you determine the stop to be hit. |
Hi @edtechre, First, we do not consider the pool bidding scenario. Here is a case:
In this case, how is the stop order filled? If the stop can't get filled on Day 3, will it place a new order in following days? Based on my understanding, pyb stop order is filled at "MARKET" price, it's not a "LIMIT" price order. Hence, I think it will be better if there is a setting, like "ctx.sell_fill_price = PriceType.OPEN", acting like "secondary" stop price option.
|
The stop is triggered if the bar's low crosses below the stop threshold, which is $75 < $98. The stop is executed on the same bar it was triggered on. The order will be placed on Day 3, bound to the low-high range of that bar: min(threshold, high) = $85. IMO it is better to be explicit and code the desired behavior yourself if you want something different than the default stop behavior. The goal of stops in Pyb is to be a simple way of approximating a lower/upper bound for losses/gains, which is the same goal of setting stops in real life. By setting a 2% stop loss, it is assumed that the stop's exit will approximate -2%. If you need a more fine tuned fill price for the stop, then you can code the desired behavior yourself using the framework's trading signals. |
Also, one more thing worth mentioning: I would be hesitant to support setting fill prices for stops because it may introduce lookahead bias, which can allow stops to have more favorable exits. This is because stops are executed on the same bar, while the normal trading signals set with buy/sell shares are placed at least one bar ahead. For example, let's say the stop's fill price would be set at the open price. But the stop was only triggered given the bar's low price (or high, or close etc.), which would have occurred after the open of the bar. And let's assume the bar opened higher than the recorded low price. Then setting the fill price to open would be the equivalent of looking ahead in time, seeing that the price will drop >= 2%, and then filling an order at the more favorable open price. It is possible to force lookahead bias into the framework, but explicitly. I would rather not introduce options that make it easier to introduce lookahead bias implicitly. |
I gave this more thought. I can add an additional option that would be used to set both the price that the stop is checked against, along with the exit price. For example: ctx.stop_trailing_exit_price = PriceType.OPEN This would check whether open <= threshold, and if true, exit at the open price on the same bar that the stop is triggered. This would get around the issue of lookahead bias I mentioned, and would allow you to specify a custom fill type, similar to what you suggested. If not set, then the stop behavior would default to the existing, where low/high prices are checked and the stop is exited at the threshold price. |
Committed the change to the dev branch. Added stop_trailing_exit_price, stop_loss_exit_price, and stop_profit_exit_price options. |
Hi @edtechre,
In the backtest, I set ctx.buy_fill_price = PriceType.OPEN and also used stop trailing. From the trade records in result, it appears that a lot of stop losses occurred on the same day as the buy, which can't be done in T+1 market, it has to be achieved at next trading day. How do I simulate such market rules inside pybroker?
The text was updated successfully, but these errors were encountered: