4. 价差可视化分析:K线图、价差曲线、相关性热力图
好,咱们进入第四讲。前面几章我们把价差的计算逻辑、数据清洗讲透了,现在该让数据「开口说话」了。
我个人习惯,拿到一组价差数据,第一件事不是跑模型,而是画图。为什么?因为图形能告诉你很多统计指标掩盖掉的细节——比如某个时间段的异常波动、结构性的偏移、或者某些品种之间「说不清道不明」的联动关系。
这一章,咱们就聚焦三种最常用的可视化手段:价差K线图、价差曲线、相关性热力图。这三种图,基本覆盖了从微观到宏观、从单品种到多品种的分析需求。
4.1 价差K线图:把价差当「品种」来交易
很多新手做套利,只看价差的收盘价序列。这其实不够。你想想看,价差在一天之内可能剧烈波动,只看收盘价会错过很多日内交易机会。
我的做法是:把价差当成一个独立的交易品种,给它画K线图。这样你就能看到价差的开盘、最高、最低、收盘,也就是OHLC数据。
下面这段代码,演示如何从两个期货合约的分钟数据生成价差K线:
import pandas as pd
import mplfinance as mpf
# 假设 df_contract1 和 df_contract2 是分钟级OHLC数据
# 先计算每分钟的价差
df_spread = pd.DataFrame()
df_spread['open'] = df_contract1['open'] - df_contract2['open']
df_spread['high'] = df_contract1['high'] - df_contract2['high']
df_spread['low'] = df_contract1['low'] - df_contract2['low']
df_spread['close'] = df_contract1['close'] - df_contract2['close']
df_spread.index = df_contract1.index # 保持时间索引
# 用 mplfinance 画K线图
mpf.plot(df_spread, type='candle', volume=False,
title='价差K线图 - 螺纹钢与热卷',
style='charles', figsize=(12,6))
嗯,这里要注意:价差K线的最高价不一定等于两个合约最高价之差。因为两个合约的最高价可能不在同一时刻出现。所以计算时要逐笔对齐时间戳,不能偷懒。
4.2 价差曲线:趋势与回归的直观呈现
价差曲线是最基础、也最直观的图。说白了就是把价差的时间序列画成一条线。但别小看它,很多交易决策就靠这条线。
我个人习惯在价差曲线上叠加三条辅助线:
- 均值线:通常是滚动均值,比如20期或60期
- 上下轨:均值 ± k倍标准差,k一般取1.5或2
- 零轴:如果价差是经过协整回归的残差,零轴就是均衡线
我曾经犯过一个错误:用全样本均值做基准线。结果回测很漂亮,实盘一跑就亏。后来才发现,全样本均值包含了未来的数据,属于「未来函数」。正确的做法是用滚动窗口。
import matplotlib.pyplot as plt
import numpy as np
# 假设 spread 是价差序列
window = 60
spread_mean = spread.rolling(window=window).mean()
spread_std = spread.rolling(window=window).std()
upper_band = spread_mean + 2 * spread_std
lower_band = spread_mean - 2 * spread_std
plt.figure(figsize=(14,6))
plt.plot(spread.index, spread, label='价差', color='blue', alpha=0.7)
plt.plot(spread.index, spread_mean, label=f'{window}期均值', color='orange', linestyle='--')
plt.fill_between(spread.index, upper_band, lower_band, alpha=0.2, color='gray', label='±2σ 通道')
plt.axhline(0, color='red', linestyle=':', alpha=0.5)
plt.legend()
plt.title('价差曲线与布林通道')
plt.show()
4.3 相关性热力图:发现隐藏的联动关系
做跨市场套利,你不可能只盯着一对品种。很多时候,A和B的价差波动,其实是受到C的影响。这时候就需要相关性热力图来帮你「看清全局」。
我通常的做法是:计算多个品种之间的滚动相关性,而不是静态的全局相关性。因为市场环境在变,相关性也在变。
import seaborn as sns
# 假设 df_prices 是多品种的收盘价DataFrame
# 计算收益率
returns = df_prices.pct_change().dropna()
# 计算滚动相关性矩阵(这里用60期窗口)
rolling_corr = returns.rolling(window=60).corr()
# 取最新一期的相关性矩阵
latest_corr = rolling_corr.iloc[-len(df_prices.columns):].unstack().iloc[:len(df_prices.columns)]
# 或者更直接:取最后一个时间点的矩阵
latest_corr_matrix = returns.rolling(window=60).corr().groupby(level=0).last().iloc[-1].unstack()
# 画热力图
plt.figure(figsize=(10,8))
sns.heatmap(latest_corr_matrix, annot=True, cmap='coolwarm', center=0,
square=True, linewidths=0.5)
plt.title('品种间收益率滚动相关性热力图(60期)')
plt.show()
4.4 三种图的组合应用策略
这三种图不是孤立的。我一般这样组合使用:
| 分析层次 | 使用图形 | 解决什么问题 |
|---|---|---|
| 微观入场点 | 价差K线图 | 识别日内假突破、确认入场时机 |
| 中观趋势判断 | 价差曲线 + 布林通道 | 判断价差是否处于极端位置、是否均值回归 |
| 宏观品种筛选 | 相关性热力图 | 发现潜在套利对、排除伪相关品种 |
举个例子:我通过热力图发现螺纹钢和热卷的相关性在0.85以上,于是把它们作为套利对。然后看价差曲线,发现当前价差处于下轨附近。再切到分钟级K线图,确认没有出现「假突破」的形态。三图印证,我才敢下单。
4.5 本章知识体系
下面这张图,帮你把本章的核心逻辑串起来:
说白了,这三种图就是你的「三重视角」:K线图看细节,价差曲线看趋势,热力图看全局。三者结合,才能做出靠谱的交易判断。
好了,这一章就到这里。记住:图形不是装饰,是决策工具。下一章我们会把这些可视化方法应用到实盘监控中,到时候你会看到它们真正的威力。
公众号:蓝海资料掘金营,微信deep3321