talib如何计算RSI(相对强度指数)?



有谁知道talib是如何计算相对强度指数(RSI)的吗?

计算RSI有不同的方法,这取决于你是使用简单平均还是指数平滑。我已经玩了所有的,但还没有能够弄清楚如何talib计算RSI。

以下是我尝试计算RSI的一些不同方法:

我的数据是pd["close"],它是pandas.core.series.Series:

{Timestamp('2016-01-04 00:00:00'): 54.79999923706055,
Timestamp('2016-01-05 00:00:00'): 55.04999923706055,
Timestamp('2016-01-06 00:00:00'): 54.04999923706055,
Timestamp('2016-01-07 00:00:00'): 52.16999816894531,
Timestamp('2016-01-08 00:00:00'): 52.33000183105469,
Timestamp('2016-01-11 00:00:00'): 52.29999923706055,
Timestamp('2016-01-12 00:00:00'): 52.779998779296875,
Timestamp('2016-01-13 00:00:00'): 51.63999938964844,
Timestamp('2016-01-14 00:00:00'): 53.11000061035156,
Timestamp('2016-01-15 00:00:00'): 50.9900016784668,
Timestamp('2016-01-19 00:00:00'): 50.560001373291016,
Timestamp('2016-01-20 00:00:00'): 50.790000915527344,
Timestamp('2016-01-21 00:00:00'): 50.47999954223633,
Timestamp('2016-01-22 00:00:00'): 52.290000915527344,
Timestamp('2016-01-25 00:00:00'): 51.790000915527344,
Timestamp('2016-01-26 00:00:00'): 52.16999816894531,
Timestamp('2016-01-27 00:00:00'): 51.220001220703125,
Timestamp('2016-01-28 00:00:00'): 52.060001373291016,
Timestamp('2016-01-29 00:00:00'): 55.09000015258789,
Timestamp('2016-02-01 00:00:00'): 54.709999084472656,
Timestamp('2016-02-02 00:00:00'): 53.0,
Timestamp('2016-02-03 00:00:00'): 52.15999984741211,
Timestamp('2016-02-04 00:00:00'): 52.0,
Timestamp('2016-02-05 00:00:00'): 50.15999984741211,
Timestamp('2016-02-08 00:00:00'): 49.40999984741211,
Timestamp('2016-02-09 00:00:00'): 49.279998779296875,
Timestamp('2016-02-10 00:00:00'): 49.709999084472656,
Timestamp('2016-02-11 00:00:00'): 49.689998626708984,
Timestamp('2016-02-12 00:00:00'): 50.5,
Timestamp('2016-02-16 00:00:00'): 51.09000015258789}
  1. 使用简单平均:
period = 14
close_delta = pd['close'].diff()
up = close_delta.clip(lower=0)
down = -1 * close_delta.clip(upper=0)
AvgU = up.rolling(window = period).mean()
AvgD = down.rolling(window = period).mean()
rs = AvgU / AvgD
rsi_simple = 100 - (100/(1 + rs))
rsi_simple_np = np.array(rsi_simple)
rsi_simple_np

Result from approach 1: 
array([        nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan, 37.25657906,
37.93970034, 38.09925461, 49.49310243, 60.05830482, 58.56432322,
50.71895845, 51.7333353 , 45.94594218, 46.90528681, 45.81208345,
44.4607394 , 47.19999756, 39.13042092, 44.74327111, 45.67308471])
  1. 与指数加权:
period = 14
close_delta = pd['close'].diff()
up = close_delta.clip(lower=0)
down = -1 * close_delta.clip(upper=0)
up_ewm = up.ewm(com = period-1, min_periods = period).mean()
down_ewm = down.ewm(com = period-1, min_periods = period).mean()
rs_ewm = up_ewm / down_ewm
rsi_ewm = 100 - (100/(1 + rs_ewm))
rsi_ewm_np
Result from approach 2:
array([        nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan, 41.95958341,
44.87716279, 39.52759183, 45.69209969, 61.09733337, 58.84295505,
49.9171034 , 46.20901506, 45.51545438, 38.38105197, 35.91021116,
35.4838002 , 38.10194654, 38.02465245, 43.06231841, 46.47516513])
  1. With talib。肢体重复性劳损症
talib_rsi = talib.RSI(pd["close"], timeperiod=14))
The result from approach 3
array([        nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan,         nan,
nan,         nan,         nan,         nan, 37.25657906,
39.35788483, 36.10262076, 40.76765901, 53.8548396 , 52.29432162,
45.85517725, 43.05088129, 42.51751177, 36.86159232, 34.82787565,
34.47284663, 36.76885993, 36.70443892, 41.1978013 , 44.29955905])

他们使用SMMA。我相信他们这样做是为了节省计算时间。

#Import everything and get data

import yfinance as yf
import talib as ta
ticker = yf.Ticker("BTC-USD")
period = '10y' 
interval = '1d' 
data = ticker.history(interval=interval, period= period)
df = data[['Close']].copy()
df['Change'] = df['Close'] - df['Close'].shift(1)
df = df.reset_index()
df = df.rename(columns={"index": "Date"})

#获得SMMA RSI,可能需要一些清理,但结果是正确的

RSI_X = 14
RSI_X2 = RSI_X - 1
RSI_X3 = RSI_X + 1
df['Upward_Movement'] = 0
df.loc[df['Change'] >= 0, 'Upward_Movement'] = df['Change']
df['Downward_Movement'] = 0
df.loc[df['Change'] < 0, 'Downward_Movement'] = abs(df['Change'])

df['Upward_Movement_SMA'] = df['Upward_Movement'].rolling(RSI_X).mean()
df['Downward_Movement_SMA'] = df['Downward_Movement'].rolling(RSI_X).mean()
df['Upward_Movement_SMMA'] = 0
df['Upward_Movement_SMMA'].iloc[RSI_X:RSI_X3] = df['Upward_Movement_SMA'] 
df['Downward_Movement_SMMA'] = 0
df['Downward_Movement_SMMA'].iloc[RSI_X:RSI_X3] = df['Downward_Movement_SMA']
for index, row in df.iloc[RSI_X3:].iterrows():
df['Upward_Movement_SMMA'].iloc[RSI_X3:] = ((df['Upward_Movement_SMMA'].shift(1)*RSI_X2)+df['Upward_Movement'])/RSI_X
df['Downward_Movement_SMMA'].iloc[RSI_X3:] = ((df['Downward_Movement_SMMA'].shift(1)*RSI_X2)+df['Downward_Movement'])/RSI_X
df['RS'] = df['Upward_Movement_SMMA']/df['Downward_Movement_SMMA']
df['RSI'] = 100-100/(df['RS']+1)

#Get TA RSI

df['RSI_Ta'] = ta.RSI(df['Close'], timeperiod=14)

#结果
print(df[['RSI', 'RSI_Ta']])

方法2(使用指数加权)应该给出与talib相同的值。RSI,如果您使用以下参数来ewm函数:

.ewm(alpha=1/period).mean()

最新更新