
在量化交易和技术分析中,均线 是最基础也最重要的工具之一。无论你是刚入门的量化新手,还是有实战经验的老股民,理解不同种类的均线及其特点,都是构建策略前的必修课。
今天这篇文章,花姐就来系统介绍一下五种最常见的均线类型------SMA、EMA、WMA(LWMA)、TMA、VMA,以及它们的计算逻辑和实际区别。
一、什么是均线?
简单来说,均线是用来平滑时间序列波动的工具,通过对历史价格的平均,来观察趋势的方向与强度。
我们可以设定一个固定的"回看周期"(如5日、10日、30日等),每往前推进一天,就剔除最早的那个数据点、加入最新的价格,因此叫做"移动平均"。
举个例子👇:
假设我们有一组数据:
8, 10, 5, 13, 17, 19, 14, 18, 12
计算5日简单移动平均(SMA):
- 第一个值:(8 + 10 + 5 + 13 + 17) / 5 = 10.6
- 第二个值:(10 + 5 + 13 + 17 + 19) / 5 = 12.8
- 第三个值:(5 + 13 + 17 + 19 + 14) / 5 = 13.6
- 第四个值:(13 + 17 + 19 + 14 + 18) / 5 = 16.2
- 第五个值:(17 + 19 + 14 + 18 + 12) / 5 = 16.0
每次计算都是取连续5个数的平均,窗口不断向前滑动,这就是"移动"平均的精髓
想用Python跑一下这个例子的话,用 pandas
非常方便:
python
import pandas as pd
data = [8, 10, 5, 13, 17, 19, 14, 18, 12]
s = pd.Series(data)
sma_5 = s.rolling(window=5).mean()
print(sma_5.dropna()) # 输出非NaN的结果
输出就是:
go
4 10.6
5 12.8
6 13.6
7 16.2
8 16.0
dtype: float64
关于均线的周期说明
在移动平均线的交易策略中,常用的回看周期包括 5、10、20、30 、60 、120 和 250 。 这些周期可以根据不同的时间维度来设置,比如分钟级、日线、周线等,具体选择取决于交易者的策略偏好: 👉 如果偏向短线交易 ,可以使用较小的周期(如5或10); 👉 如果倾向中期交易 ,则可以选择更长的周期(如20、30、60); 👉 如果倾向趋势交易,则可以选择更长的周期(如120、250)。
不同的周期长度能帮助交易者捕捉不同级别的市场趋势,是技术分析中非常关键的一环,当然也有一些股民为了防止庄家割韭菜,搞假动作,也会采用特殊的周期来做均线,比如7、9、13之类的。
二、五种常见均线类型对比
1. 简单移动平均线(SMA:Simple Moving Average)
SMA 是最基础 、最常用的一种均线,它对所有的数据点赋予相同的权重。
公式:
<math xmlns="http://www.w3.org/1998/Math/MathML" display="block"> SMA = 周期内所有价格之和 周期数 \text{SMA} = \frac{\text{周期内所有价格之和}}{\text{周期数}} </math>SMA=周期数周期内所有价格之和
优点:
- 简单直观,计算方便 缺点:
- 对价格变动反应慢,有"滞后性"
下面是一个使用 AKShare 获取 沪深300指数最近两年数据,并用 matplotlib 绘制 收盘价 + 5日、10日、20日简单移动平均线(SMA) 的完整 Python 示例代码,我们看看SMA的走势如何
python
import akshare as ak
import pandas as pd
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
# 1. 获取最近2年的日期范围
end_date = datetime.today()
start_date = end_date - timedelta(days=365 * 2)
start_str = start_date.strftime("%Y%m%d")
end_str = end_date.strftime("%Y%m%d")
# 2. 获取沪深300指数的历史行情数据(指数代码:000300.SH)
df = ak.index_zh_a_hist(
symbol="000300",
period="daily",
start_date=start_str,
end_date=end_str)
# 3. 数据预处理
df['日期'] = pd.to_datetime(df['日期'])
df.set_index('日期', inplace=True)
df.sort_index(inplace=True)
# 4. 计算移动平均线
df['MA5'] = df['收盘'].rolling(window=5).mean()
df['MA10'] = df['收盘'].rolling(window=10).mean()
df['MA20'] = df['收盘'].rolling(window=20).mean()
# 5. 绘图
plt.rcParams['font.sans-serif'] = ['SimHei'] # 使用黑体
plt.rcParams['axes.unicode_minus'] = False # 正确显示负号
plt.figure(figsize=(14, 6))
plt.plot(df.index, df['收盘'], label='收盘价', color='black', linewidth=1)
plt.plot(df.index, df['MA5'], label='5日均线', color='pink', linewidth=1)
plt.plot(df.index, df['MA10'], label='10日均线', color='orange', linewidth=1)
plt.plot(df.index, df['MA20'], label='20日均线', color='red', linewidth=1)
plt.title('沪深300指数 - 收盘价与移动平均线(近两年)', fontsize=14)
plt.xlabel('日期')
plt.ylabel('指数点位')
plt.legend()
plt.grid(True)
plt.tight_layout()
plt.show()

5日、10日、20日简单移动平均线(SMA)与价格的关系,可以反映出市场的短中期趋势强弱和多空力量的转换。通常来说,价格位于三条均线之上,且均线呈多头排列(即5日在线上、10日居中、20日最下方),说明当前市场处于明显的上升趋势中,多头占据主动;相反,若价格位于三线下方,且均线呈空头排列,则市场处于下跌趋势,空头占优。当价格上穿或下穿其中一条或多条均线,往往预示着短期趋势的改变,比如价格突破并站稳20日线,可能代表中期趋势由弱转强,而跌破20日线则需警惕趋势反转风险。另外,当均线之间距离逐渐收窄并形成粘合状态,说明市场进入震荡整理阶段,此时方向尚未明朗,价格对均线的突破往往成为下一波行情的启动信号。因此,价格与5/10/20日均线之间的相对位置、穿越关系和排列顺序,是判断市场短中期趋势的关键依据,适合用于趋势判断、回调买入、止盈止损等多种策略场景。
2. 指数移动平均线(EMA:Exponential Moving Average)
EMA 给近期的价格赋予更高的权重,比 SMA 更快响应价格变化。
计算方式略复杂,但可使用如下公式近似理解:
<math xmlns="http://www.w3.org/1998/Math/MathML" display="block"> EMA = 收盘价 × 权重 + 前一日 EMA × ( 1 − 权重 ) \text{EMA} = \text{收盘价} \times \text{权重} + \text{前一日 EMA} \times (1 - \text{权重}) </math>EMA=收盘价×权重+前一日 EMA×(1−权重)
其中:
<math xmlns="http://www.w3.org/1998/Math/MathML" display="block"> 权重 = 2 n + 1 \text{权重} = \frac{2}{n + 1} </math>权重=n+12
优点:
- 响应更迅速,适合捕捉趋势转折 缺点:
- 可能对噪声反应过度,产生"假信号"
下面是一个使用 AKShare 获取 沪深300指数最近两年数据,并用 matplotlib 绘制 收盘价 + 20日简单移动平均线(SMA)和 指数移动平均线(EMA)的完整 Python 示例代码,我们看看两者的走势有何差异
python
import akshare as ak
import pandas as pd
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
# 获取日期范围(最近两年)
end_date = datetime.today()
start_date = end_date - timedelta(days=365 * 2)
start_str = start_date.strftime("%Y%m%d")
end_str = end_date.strftime("%Y%m%d")
# 获取沪深300指数数据
df = ak.index_zh_a_hist(
symbol="000300",
period="daily",
start_date=start_str,
end_date=end_str)
# 数据预处理
df['日期'] = pd.to_datetime(df['日期'])
df.set_index('日期', inplace=True)
df.sort_index(inplace=True)
# 计算20日 SMA 和 EMA
df['SMA20'] = df['收盘'].rolling(window=20).mean()
df['EMA20'] = df['收盘'].ewm(span=20, adjust=False).mean()
# 绘图
plt.rcParams['font.sans-serif'] = ['SimHei'] # 使用黑体
plt.rcParams['axes.unicode_minus'] = False # 正确显示负号
plt.figure(figsize=(14, 6))
plt.plot(df.index, df['收盘'], label='收盘价', color='black', linewidth=1)
plt.plot(df.index, df['SMA20'], label='SMA20(简单均线)', color='blue', linewidth=1.5)
plt.plot(df.index, df['EMA20'], label='EMA20(指数均线)', color='red', linestyle='--', linewidth=1.5)
plt.title('沪深300指数 - 收盘价 vs 20日SMA & EMA', fontsize=14)
plt.xlabel('日期')
plt.ylabel('指数点位')
plt.legend()
plt.grid(True)
plt.tight_layout()
plt.show()

根据SMA和EMA的20日均线与价格的关系,我们可以发现它们在衡量市场中期趋势时各有侧重:SMA20反应较为平滑,适合识别稳定的趋势方向,而EMA20对价格变动更敏感,更适合捕捉趋势的起点或反转信号。当价格持续运行在SMA20和EMA20上方,说明市场处于健康的上升趋势中,多头力量占优;反之,若价格跌破这两条均线,且均线拐头向下,往往预示着趋势减弱或反转,空头开始掌控主动。如果价格在SMA20附近震荡而EMA20频繁穿越价格,则可能意味着市场进入盘整阶段,趋势方向不明确。此外,EMA20上穿SMA20往往代表短期多头力量增强,有可能引发新一轮上涨,而EMA20下穿SMA20则可能预示市场将进入调整。总的来看,结合SMA20的趋势稳定性与EMA20的响应速度,可以更全面地判断当前价格的中期趋势强弱与潜在拐点。
3. 线性加权移动平均线(LWMA/WMA:Linearly Weighted Moving Average)
WMA 与 EMA 同样是加权平均,但权重是线性递增,比如10日 LWMA 就是第10天权重为10,第9天为9,依此类推。
公式:
<math xmlns="http://www.w3.org/1998/Math/MathML" display="block"> WMA = ∑ ( 价格 × 线性权重 ) ∑ ( 权重 ) \text{WMA} = \frac{\sum(\text{价格} \times \text{线性权重})}{\sum(\text{权重})} </math>WMA=∑(权重)∑(价格×线性权重)
优点:
- 比 EMA 更强调最近数据 缺点:
- 对极端价格更敏感,容易产生尖锐波动
同样我们把SMA、EMA、WMA绘制到同一张图中,方便我们观察,以下是一个Python示例代码:
python
import akshare as ak
import pandas as pd
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
import numpy as np
# 1. 获取日期范围(最近两年)
end_date = datetime.today()
start_date = end_date - timedelta(days=365 * 2)
start_str = start_date.strftime("%Y%m%d")
end_str = end_date.strftime("%Y%m%d")
# 2. 获取沪深300指数数据
df = ak.index_zh_a_hist(
symbol="000300",
period="daily",
start_date=start_str,
end_date=end_str)
# 3. 数据预处理
df['日期'] = pd.to_datetime(df['日期'])
df.set_index('日期', inplace=True)
df.sort_index(inplace=True)
# 4. 计算20日均线
df['SMA20'] = df['收盘'].rolling(window=20).mean()
df['EMA20'] = df['收盘'].ewm(span=20, adjust=False).mean()
# 5. 计算WMA20(加权移动平均)
def weighted_moving_average(series, window):
weights = np.arange(1, window + 1)
return series.rolling(window).apply(lambda prices: np.dot(prices, weights)/weights.sum(), raw=True)
df['WMA20'] = weighted_moving_average(df['收盘'], 20)
# 6. 绘图
plt.rcParams['font.sans-serif'] = ['SimHei'] # 使用黑体
plt.rcParams['axes.unicode_minus'] = False # 正确显示负号
plt.figure(figsize=(14, 6))
plt.plot(df.index, df['收盘'], label='收盘价', color='black', linewidth=1)
plt.plot(df.index, df['SMA20'], label='SMA20(简单均线)', color='blue', linewidth=1.5)
plt.plot(df.index, df['EMA20'], label='EMA20(指数均线)', color='red', linestyle='--', linewidth=1.5)
plt.plot(df.index, df['WMA20'], label='WMA20(加权均线)', color='green', linestyle='-.', linewidth=1.5)
plt.title('沪深300指数 - 收盘价与20日SMA / EMA / WMA 对比图', fontsize=14)
plt.xlabel('日期')
plt.ylabel('指数点位')
plt.legend()
plt.grid(True)
plt.tight_layout()
plt.show()

SMA、EMA 和 WMA 是量化交易中最常用的三种均线形式,各自适用于不同的策略场景。SMA 计算简单,适合用于趋势确认、支撑阻力判断等稳健策略,但响应慢,容易滞后于行情;EMA 对新数据加权更高,能更快响应价格变化,常用于构建动量策略、趋势跟踪系统以及短期交易信号捕捉;WMA 在加快响应的同时对最新价格给予最大权重,比 EMA 更敏感,适合用于对价格变动反应要求更快的策略,比如高频信号生成或短周期反转策略。三者在实盘应用中通常配合使用,通过交叉、偏离、组合等方式判断多空转换、跟踪趋势强弱或作为交易信号过滤条件,是构建多因子模型或交易系统的基础工具。
4. 三角移动平均线(TMA:Triangular Moving Average)
TMA 是对 SMA 再进行一次平均,等于"双重平滑"。
计算方式:
- 第一步:计算 SMA
- 第二步:对 SMA 再做一次均值(再次滚动)
优点:
- 曲线平滑、噪声少 缺点:
- 滞后性最强,反应慢
以下是EMA和TMA绘制20日均线的简单Python示例
python
import akshare as ak
import pandas as pd
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
# 1. 获取日期范围(最近两年)
end_date = datetime.today()
start_date = end_date - timedelta(days=365 * 2)
start_str = start_date.strftime("%Y%m%d")
end_str = end_date.strftime("%Y%m%d")
# 2. 获取沪深300指数数据
df = ak.index_zh_a_hist(
symbol="000300",
period="daily",
start_date=start_str,
end_date=end_str)
# 3. 数据预处理
df['日期'] = pd.to_datetime(df['日期'])
df.set_index('日期', inplace=True)
df.sort_index(inplace=True)
# 4. 计算20日 SMA
df['SMA20'] = df['收盘'].rolling(window=20).mean()
# 5. 计算20日 TMA(对SMA再做一次SMA)
df['TMA20'] = df['SMA20'].rolling(window=20).mean()
# 6. 绘图
plt.rcParams['font.sans-serif'] = ['SimHei'] # 使用黑体
plt.rcParams['axes.unicode_minus'] = False # 正确显示负号
plt.figure(figsize=(14, 6))
plt.plot(df.index, df['收盘'], label='收盘价', color='black', linewidth=1)
plt.plot(df.index, df['SMA20'], label='SMA20(简单移动平均)', color='blue', linewidth=1.5)
plt.plot(df.index, df['TMA20'], label='TMA20(三角移动平均)', color='purple', linestyle='--', linewidth=1.5)
plt.title('沪深300指数 - 收盘价与20日SMA / TMA 对比图', fontsize=14)
plt.xlabel('日期')
plt.ylabel('指数点位')
plt.legend()
plt.grid(True)
plt.tight_layout()
plt.show()

EMA 和 TMA 在量化交易中都被广泛用于趋势识别与信号构建,其中 EMA 因为对近期价格反应更敏感,常被用于捕捉短期价格变化,用作交易信号的核心触发条件,尤其适合动量策略、趋势突破和跟踪系统,在多均线交叉、回调入场等场景中表现突出;而 TMA 由于是对简单均线的二次平滑,波动更小、滞后性更强,常用于中长期趋势的确认与噪声过滤,适合在震荡市场中作为趋势滤波器或慢速参考线,避免频繁误判信号;在实盘策略中,两者可以结合使用,例如以 EMA 作为快速信号线,TMA 作为慢速趋势确认,有效平衡信号灵敏度与稳定性,提升交易系统的鲁棒性与容错能力。
5. 可变移动平均线(VMA:Variable Moving Average)
VMA 是一种基于波动率动态调整权重的移动平均。当价格波动大时,它更敏感;当市场平稳时,它变得更平滑。
优点:
- 能自适应市场环境变化 缺点:
- 实现稍复杂,需计算波动率或相关指标(如 ATR)
接下来我们用Python绘制一个VMA和EMA的对比图,为什么拿他俩对比,而不和其它的均线对比呢?
原因如下👇:
-
核心思想相似: VMA 和 EMA 都是"加权"均线,重点是对近期价格赋予更高权重,但 VMA 进一步引入了"波动性因子"或"动态权重调整",根据市场波动自动调整平滑系数,响应更灵活;
-
对比价值高: EMA 是固定平滑系数,适合稳定市场;VMA 根据市场波动变动权重,适合波动市场。两者的对比可以揭示 VMA 的自适应特性是否能更好地捕捉趋势或避免震荡陷阱;
-
实际策略中常作为替代品: 很多量化策略在优化EMA参数时,可能会考虑用VMA替换EMA,作为提升信号质量的手段;
以下是代码部分:
python
import akshare as ak
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
# 1. 获取沪深300指数最近两年数据
end_date = datetime.today()
start_date = end_date - timedelta(days=365 * 2)
start_str = start_date.strftime("%Y%m%d")
end_str = end_date.strftime("%Y%m%d")
df = ak.index_zh_a_hist(
symbol="000300",
period="daily",
start_date=start_str,
end_date=end_str)
df['日期'] = pd.to_datetime(df['日期'])
df.set_index('日期', inplace=True)
df.sort_index(inplace=True)
# 2. 计算标准20日EMA
df['EMA20'] = df['收盘'].ewm(span=20, adjust=False).mean()
# 3. 自定义计算20日VMA(根据价格波动动态调整 alpha)
def calc_vma(price_series, base_span=20, fast_alpha=2/(5+1), slow_alpha=2/(40+1)):
vma = []
last_vma = price_series.iloc[0]
for i in range(1, len(price_series)):
# 计算波动率(这里简单使用前一日涨跌幅作为波动因子)
delta = abs(price_series.iloc[i] - price_series.iloc[i - 1])
vol = delta / price_series.iloc[i - 1] if price_series.iloc[i - 1] != 0 else 0
# 动态 alpha:波动越大,alpha 越接近 fast;波动越小,越接近 slow
dynamic_alpha = slow_alpha + (fast_alpha - slow_alpha) * min(vol * 100, 1)
# VMA更新
last_vma = dynamic_alpha * price_series.iloc[i] + (1 - dynamic_alpha) * last_vma
vma.append(last_vma)
vma = [np.nan] + vma # 与原始价格长度对齐
return vma
df['VMA20'] = calc_vma(df['收盘'])
# 4. 绘图
plt.rcParams['font.sans-serif'] = ['SimHei'] # 使用黑体
plt.rcParams['axes.unicode_minus'] = False # 正确显示负号
plt.figure(figsize=(14, 6))
plt.plot(df.index, df['收盘'], label='收盘价', color='black', linewidth=1)
plt.plot(df.index, df['EMA20'], label='EMA20(固定权重)', color='red', linewidth=1.5)
plt.plot(df.index, df['VMA20'], label='VMA20(可变权重)', color='blue', linestyle='--', linewidth=1.5)
plt.title('沪深300指数 - EMA vs VMA 对比图', fontsize=14)
plt.xlabel('日期')
plt.ylabel('指数点位')
plt.legend()
plt.grid(True)
plt.tight_layout()
plt.show()
VMA在量化中的应用主要体现在它对市场波动的自适应能力,使其在不同波动环境下都能保持较高的信号质量,适合用于趋势跟踪、动量策略和信号过滤等多个方向,相较于固定参数的EMA,VMA能够在行情剧烈波动时自动提高灵敏度,快速响应趋势变化,在行情平稳时又能降低噪声干扰、避免频繁交易,因此非常适合用于构建动态交易信号线、作为均线交叉策略中的灵活一环、或者作为量化模型中平滑处理因子的自适应替代方案,同时VMA还能配合波动率指标(如ATR)进一步优化入场和离场时机,是在实际策略中兼顾响应性与稳定性的优选工具。
四、总结对比表
类型 | 权重特点 | 响应速度 | 是否平滑 | 适合场景 |
---|---|---|---|---|
SMA | 平均权重 | 慢 | 高 | 长期趋势判断 |
EMA | 指数加权 | 快 | 中 | 短期转折捕捉 |
LWMA | 线性加权 | 快 | 低 | 高频波动场景 |
TMA | 双重平均 | 最慢 | 非常高 | 震荡行情过滤噪声 |
VMA | 动态权重 | 适中 | 自适应 | 高频策略、动态市场 |
五、如何选择?
不同均线适配不同的风格,在量化中选择哪种均线,核心在于策略目标、交易周期、对信号响应速度的要求
-
SMA 适合用于中长期趋势判断、支撑阻力参考或回测中的基础基准,优点是稳定、简单、可解释性强,缺点是反应滞后,不适合快速市场;
-
EMA 适合用在需要较快反应市场变化的策略中,常用于短期趋势捕捉、动量入场信号构建以及均线交叉策略,适合日内和波段交易;
-
WMA 在响应速度上介于EMA与SMA之间,适合需要权重更偏向近期价格的策略,比如短线均线跟随或价格反转识别;
-
TMA 是对SMA的再次平滑处理,更平滑但滞后更明显,适合震荡市场中用于趋势确认或防止噪声干扰,常用于做信号过滤器或辅助线;
-
VMA 具备自适应性,是最灵活的均线之一,能根据市场波动自动调整响应速度,适合构建具备动态响应能力的趋势策略,特别适用于波动性变化剧烈的市场环境。
总结来说,短线快节奏交易偏向用EMA/WMA,追求稳定信号用SMA/TMA,想提升自适应能力就选VMA,实战中常会组合使用,以平衡反应速度与稳定性。
今天关于量化中均线的介绍就到这里了。