«

【原生代码】Python3 计算DI、ADX趋向指标

时间:2021-11-13 21:16     作者:苏慕白     分类: 指标


1.引用:

import pandas as pd
import numpy as np

2.代码

#RSI中使用的移动平均线。 它是指数加权移动平均线,alpha加权值 = 1 /长度
def RMA(r, days, name=0):
    cps = [ v[name] for v in r ] if name else r
    rmas = [0 for i in range(len(cps))]  # 创造一个和cps一样大小的集合
    alpha = 1 / days

    for i in range(len(cps)):
        if i > days-1:
            if rmas[i-1] and not np.isnan(rmas[i-1]):
                rmas[i] = alpha * cps[i] + (1 - alpha) * rmas[i-1]
            else:
                ma = 0
                for i2 in range(i-days,i):  #求平均值
                    ma += cps[i2+1]
                rmas[i] = ma / days

    return rmas

#其他MA类型看上一篇文章
def ATR(r, days, ma='sma'):
    tr = [0]
    for i in range(len(r)):
        if i:
            tr.append(max(r[i]['High']-r[i]['Low'], abs(r[i]['High'] - r[i-1]['Close']), abs(r[i]['Low'] - r[i-1]['Close'])))

    if ma == 'rma':
        return RMA(tr, days)

    if ma == 'ema':
        return EMA(tr, days)

    if ma == 'sma':
        return SMA(tr, days)

    if not ma:
        return tr

"""DI"""
def DI(r, days):
    df = pd.DataFrame(r)
    df['up'] = df['High'] - df['High'].shift(1)
    df['down'] = -(df['Low'] - df['Low'].shift(1))
    df['truerange'] = RMA(ATR(r, days=0, ma=0), days)
    df['plus'] = RMA([df['up'][i] if df['up'][i] > df['down'][i] and df['up'][i]> 0 else 0 for i in range(len(df['up']))], days) / df['truerange']
    df['minus'] = RMA([df['down'][i] if df['down'][i] > df['up'][i] and df['down'][i]> 0 else 0 for i in range(len(df['up']))], days) / df['truerange']

    df['plus'] = df['plus'].apply(float) * 100
    df['minus'] = df['minus'].apply(float) * 100
    return df['plus'], df['minus']

"""ADX趋向指标"""
def ADX(r, diDays, adxDays):
    df = pd.DataFrame(r)
    df['plus'], df['minus'] = DI(r, diDays)
    df['sum'] = df['plus'] + df['minus']
    df['adx'] = [abs(df['plus'][i] - df['minus'][i]) / (1 if df['sum'][i] == 0 else df['sum'][i]) for i in range(len(df['sum']))]
    df['adx'] = RMA(df['adx'].values, adxDays)
    df['adx'] = df['adx'].apply(float) * 100

    return df['adx'], df['plus'], df['minus']

3.使用例子

指标计算的值我都和TradingView对比过,放心使用~
r为K线数据

df['adx'], df['plus'], df['minus'] = ADX(r, 14, 14)

图片alt