'How to get alternating trading signals?

I am trying to develop a simple RSI strategy by using this code. As you can see by plotting the code, there are too many consecutive sell signals. I'd like there were buy signals followed by a SINGLE sell signal and, after that, another buy signal in order to have, at the end, something like buy, sell, buy, sell... and not something like buy, sell, sell, sell, sell, buy, sell, sell... Here you are the code:

import yfinance as yf
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import datetime as dt
import ta

start = dt.datetime(2020, 1, 1)
df = yf.download("^GSPC", start)

portfolio = 10000

df['rsi'] = ta.momentum.rsi(df.Close, window=10)
df['200ma'] = df.Close.rolling(200).mean()
df.dropna(inplace=True)


buy, sell = [], []

for i in range(1, len(df)):
    if df.Close.iloc[i] > df['200ma'].iloc[i]:
        if df['rsi'].iloc[i] < 30:
            buy.append(i)
        elif df['rsi'].iloc[i] > 40 or ((df['rsi'].iloc[i] - df.Close.iloc[i]) > 10):
            sell.append(i)

realbuys = [i+1 for i in buy]
realsells = [i+1 for i in sell]

buyprices = df.Open.iloc[realbuys]
sellprices = df.Open.iloc[realsells]

# plt.figure(figsize = (12, 6))
# plt.scatter(df.iloc[buy].index, df.iloc[buy].Close, marker = "^", color = "green" )
# plt.scatter(df.iloc[sell].index, df.iloc[sell].Close, marker = "v", color = "red" )
# plt.plot(df.Close, label = "S&P", color='k')
# plt.legend()
# plt.show()


pnl = []

for i in range(len(sellprices)):
    pnl.append(((sellprices[i] - buyprices[i])/buyprices[i]))

    portfolio = portfolio + (portfolio * pnl[i])
    
averagepnl = sum(pnl) / len(pnl)

print(portfolio, averagepnl)


Solution 1:[1]

So. A variable 'order' has been created, in which we record the current transaction. As you will notice, the entry into the transaction occurs only in the opposite direction. For example, if you bought it now, then the next transaction will only be a sale. Or any transaction, if it's the first one.

In the portfolio, I purposefully reduced the cycle by one element. Since buying and selling transactions are not the same. That is, the current sale is not closed.

import yfinance as yf
import matplotlib.pyplot as plt
import datetime as dt
import ta

start = dt.datetime(2020, 1, 1)
df = yf.download("^GSPC", start)

portfolio = 10000

df['rsi'] = ta.momentum.rsi(df.Close, window=10)
df['200ma'] = df.Close.rolling(200).mean()
df.dropna(inplace=True)

buy, sell = [], []
order = ''
for i in range(1, len(df)):
    if df.Close.iloc[i] > df['200ma'].iloc[i]:
        if df['rsi'].iloc[i] < 30:
            if order == 'sell' or order == '':
                buy.append(i)
                order = 'buy'
        elif df['rsi'].iloc[i] > 40 or ((df['rsi'].iloc[i] - df.Close.iloc[i]) > 10):
            if order == 'buy' or order == '':
                sell.append(i)
                order = 'sell'

realbuys = [i + 1 for i in buy]
realsells = [i + 1 for i in sell]

buyprices = df.Open.iloc[realbuys]
sellprices = df.Open.iloc[realsells]

plt.figure(figsize = (12, 6))
plt.scatter(df.iloc[buy].index, df.iloc[buy].Close, marker = "^", color = "green" )
plt.scatter(df.iloc[sell].index, df.iloc[sell].Close, marker = "v", color = "red" )
plt.plot(df.Close, label = "S&P", color='k')
plt.legend()
plt.show()


pnl = []

for i in range(len(sellprices)-1):
    pnl.append(((sellprices[i] - buyprices[i]) / buyprices[i]))

    portfolio = portfolio + (portfolio * pnl[i])

averagepnl = sum(pnl) / len(pnl)

print(portfolio, averagepnl)

enter image description here

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 inquirer