# 【原生代码】Python3 实现ATR、MA、EMA、SMMA、RMA、TEMA指标的计算

Author: 苏慕白, Created: 2021-11-01 20:11:24, Updated: 2021-11-01 20:11:57

### 1. 参数说明

r：K线数据，字典或者数组 days：指标长度 name：使用哪一个字段，填’Close’即可，如果不填则代表r是数组而不是字典

``````{
{
'Time': 0,
'Close': 0,
'Open': 0,
'High': 0,
'Low': 0,
'Volume': 0,
}
}
``````

### 2. ATR 真实波动幅度 （需配合下面的指标）

``````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)

return SMA(tr, days)
``````

### 3. MA 移动平均线

``````def SMA(r, days, name=0):
cps = [ v[name] for v in r ] if name else r
emas = cps.copy()  # 创造一个和cps一样大小的集合

for i in range(len(cps)):
if i < days-1:
emas[i] = 0
else:
ma = 0
for i2 in range(i-days,i):
i2 += 1
ma += cps[i2]
emas[i] = ma / days
return emas
``````

### 4. EMA 指数移动平均线

``````def EMA(r, days, name=0):

if name == 'o+h+l+c':
cps = [ (v['Open'] + v['High'] + v['Low'] + v['Close']) / 4 for v in r ]

elif name == 'h+l+c':
cps = [ (v['High'] + v['Low'] + v['Close']) / 3 for v in r ]

elif name == 'h+l':
cps = [ (v['High'] + v['Low']) / 2 for v in r ]

else:
cps = [ v[name] for v in r ] if name else r

emas = [0 for i in range(len(cps))]  # 创造一个和cps一样大小的集合
for i in range(len(cps)):
if i == 0:
emas[i] = cps[i]
if i > 0:
emas[i] = ((days - 1) * emas[i - 1] + 2 * cps[i]) / (days + 1)

emas = [v for v in emas]
return emas
``````

### 5. SMMA 平滑移动平均线

``````def SMMA(r, days, name=0):
cps = [ v[name] for v in r ] if name else r
emas = [0 for i in range(len(cps))]  # 创造一个和cps一样大小的集合
ma = 0
for i in range(len(cps)):
if i < days:
ma += cps[i]
emas[i] = 0

else:
if emas[i-1] == 0:
emas[i] = ma / days
else:
emas[i] = (emas[i-1] * (days - 1) + cps[i]) / days

emas = [v for v in emas]
return emas
``````

### 6. RMA，RSI中使用的移动平均线，它是指数加权移动平均线

``````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:
rmas[i] = 0
else:
if 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
``````

### 7. TEMA 三重指数平滑移动平均线

``````def TEMA(r, days, name='Close'):
v2 = EMA(r, days, name)
v3 = EMA(v2, days)
v4 = EMA(v3, days)

emas = []
for i in range(len(v2)):
ok = 3 * (v2[i] - v3[i]) + v4[i]
emas.append(ok)
return emas
``````

More