I have a dataframe with a price series and the z-score of that price series. I want to create a signal variable for buy and sell signals with the following conditions:
- Buy signal (=1) if the normalised price crosses -1.96 standard deviation below the mean and close the the buy position when it crosses the mean from below
- Sell signal (=-1) if the normalised price crosses +1.96 standard deviation above the mean and close the the short position when it crosses the mean from above.
I can create the buy and sell signals using np.where when the normalised variable crosses the upper and lower bounds, but I'm trying to keep the position until it crosses the mean.
Code below:
# Create a DataFrame with the signal and position size in the pair
trades = pd.concat([zscore(df_kalman), df_kalman], axis=1)
trades.columns = ["signal", "position"]
trades['mean'] = trades['signal'].mean()
trades['upper'] = trades['mean'] + 1.96*trades['signal'].std()
trades['lower'] = trades['mean'] - 1.96*trades['signal'].std()
trades["side"] = 0.0
trades['side'] = np.where((trades['signal'] > trades['upper']), -1, 0)
trades['side'] = np.where(((trades['signal'] > trades['mean']) & (trades['side'].shift(1) == -1)), -1, trades['side'])
trades['side'] = np.where((trades['signal'] < trades['lower']), 1, trades['side'])
trades['side'] = np.where(((trades['signal'] < trades['mean']) & (trades['side'].shift(1) == 1)), 1, trades['side'])
Plot below:

you are trying to create trading signals based on z-scores and certain conditions. If you want to keep the position until it crosses the mean, you can adjust your logic. Here's the modified code: