For code/output blocks: Use ``` (aka backtick or grave accent) in a single line before and after the block. See: http://commonmark.org/help/

Stochastic RSI indicator.



  • Hi colleagues.
    I've finished stoch RSI indicator and i would like to share it. It has the same K & D values as the Tradingview stoch RSI.
    https://www.tradingview.com/wiki/Stochastic_RSI_(STOCH_RSI)

    My applauds to the Backtrader developers team - excellent platform. Any comments are welcome.

    from backtrader.indicators import Indicator, MovAv, RelativeStrengthIndex, Highest, Lowest
    class StochasticRSI(Indicator):
          """
          K - The time period to be used in calculating the %K. 3 is the default.
          D - The time period to be used in calculating the %D. 3 is the default.
          RSI Length - The time period to be used in calculating the RSI
          Stochastic Length - The time period to be used in calculating the Stochastic
      
          Formula:
          %K = SMA(100 * (RSI(n) - RSI Lowest Low(n)) / (RSI HighestHigh(n) - RSI LowestLow(n)), smoothK)
          %D = SMA(%K, periodD)
      
          """
          lines = ('fastk', 'fastd',)
      
          params = (
              ('k_period', 3),
              ('d_period', 3),
              ('rsi_period', 14),
              ('stoch_period', 14),
              ('movav', MovAv.Simple),
              ('rsi', RelativeStrengthIndex),
              ('upperband', 80.0),
              ('lowerband', 20.0),
          )
      
          plotlines = dict(percD=dict(_name='%D', ls='--'),
                           percK=dict(_name='%K'))
      
          def _plotlabel(self):
              plabels = [self.p.k_period, self.p.d_period, self.p.rsi_period, self.p.stoch_period]
              plabels += [self.p.movav] * self.p.notdefault('movav')
              return plabels
      
          def _plotinit(self):
              self.plotinfo.plotyhlines = [self.p.upperband, self.p.lowerband]
      
          def __init__(self):
              rsi_hh = Highest(self.p.rsi(period=self.p.rsi_period), period=self.p.stoch_period)
              rsi_ll = Lowest(self.p.rsi(period=self.p.rsi_period), period=self.p.stoch_period)
              knum = self.p.rsi(period=self.p.rsi_period) - rsi_ll
              kden = rsi_hh - rsi_ll
      
              self.k = self.p.movav(100.0 * (knum / kden), period=self.p.k_period)
              self.d = self.p.movav(self.k, period=self.p.d_period)
      
              self.lines.fastk = self.k
              self.lines.fastd = self.d


  • Thank you!

    What is the difference between your implementation and bt built-in implementation?



  • @ab_trader
    I did not find StochRSI in bt. As i see, it has only Stochastic and RSI as a separate indicators. TA-lib StochRSI has K & D values other than Tradingview.
    Tradingview (TV) is a rapidly growing JS framwork. The goal was to receive exact the same values as TV.


  • administrators

    StochRSI is a well known indicator, not something which has been invented by Tradingview.

    You probably want to rewrite this

    @nikolai said in Stochastic RSI indicator.:

          def __init__(self):
              rsi_hh = Highest(self.p.rsi(period=self.p.rsi_period), period=self.p.stoch_period)
              rsi_ll = Lowest(self.p.rsi(period=self.p.rsi_period), period=self.p.stoch_period)
              knum = self.p.rsi(period=self.p.rsi_period) - rsi_ll
              kden = rsi_hh - rsi_ll
      
              self.k = self.p.movav(100.0 * (knum / kden), period=self.p.k_period)
              self.d = self.p.movav(self.k, period=self.p.d_period)
      
              self.lines.fastk = self.k
              self.lines.fastd = self.d
    

    to look like this (and avoid unnecessary instantiation of multiple indicators and unneeded member attributes)

        def __init__(self):
            rsi = bt.ind.RSI(period=self.p.rsi_period)
            rsi_ll = bt.ind.Lowest(rsi, period=self.p.rsi_period)
            rsi_hh = bt.ind.Highest(rsi, period=self.p.rsi_period)
            stochrsi = (rsi - rsi_ll) / (rsi_hh - rsi_ll)
    
            self.l.fastk = k = self.p.movav(100.0 * stochrsi, period=self.p.k_period)
            self.l.fastd = self.p.movav(k, period=self.p.d_period)
    


  • @backtrader, thanks for help with the code. Tradingview didn't invent StochRSI of course. Their docs are a bit messy for this indicator. So, the goal was to get the same implementation.