3、A股分钟数据获取:Tushare Pro分钟数据接口、数据拼接与对齐、处理复权因子
各位同学,今天我们来聊聊分钟数据。
说实话,做量化交易,日线数据只是入门。真正想捕捉短线机会,分钟数据才是核心武器。我刚开始做高频策略时,就吃过分钟数据不对齐的亏——回测曲线漂亮得像假的一样,实盘一跑直接崩了。嗯,今天就把这些坑都给你们填上。
3.1 Tushare Pro分钟数据接口
Tushare Pro 提供了 pro.minute() 接口,可以获取指定股票的分钟级行情。我个人习惯用这个接口来拉取最近一段时间的分钟K线。
先看一个最基本的调用示例:
import tushare as ts
# 初始化pro接口
pro = ts.pro_api('你的token')
# 获取平安银行2023年1月4日的分钟数据
df = pro.minute(ts_code='000001.SZ', start_date='20230104', end_date='20230104')
print(df.head())
返回的数据结构是这样的:
| 字段名 | 含义 | 示例值 |
|---|---|---|
| ts_code | 股票代码 | 000001.SZ |
| trade_time | 交易时间 | 2023-01-04 09:31:00 |
| open | 开盘价 | 12.35 |
| high | 最高价 | 12.42 |
| low | 最低价 | 12.30 |
| close | 收盘价 | 12.38 |
| vol | 成交量(手) | 15234 |
| amount | 成交额(元) | 1887654.0 |
小提示: 这个接口每次最多返回6000条记录。如果你要拉取多天的数据,建议按天循环请求,别一次性拉太久。
3.2 数据拼接与对齐
单只股票的分钟数据好拿,但做策略时往往需要多只股票同时分析。这时候就涉及到数据拼接和对齐的问题了。
我曾经遇到过一个情况:两只股票,一只在09:31有数据,另一只在09:32才有。如果直接横向拼接,时间戳对不上,计算出来的相关性全是错的。
正确的做法是:先按时间索引对齐,再拼接。
来看代码:
import pandas as pd
# 假设我们有两支股票的分钟数据
stock_a = pro.minute(ts_code='000001.SZ', start_date='20230104', end_date='20230104')
stock_b = pro.minute(ts_code='000002.SZ', start_date='20230104', end_date='20230104')
# 将trade_time设为索引
stock_a.set_index('trade_time', inplace=True)
stock_b.set_index('trade_time', inplace=True)
# 只保留收盘价
close_a = stock_a[['close']].rename(columns={'close': '000001_close'})
close_b = stock_b[['close']].rename(columns={'close': '000002_close'})
# 按时间索引对齐合并
merged = pd.concat([close_a, close_b], axis=1, join='inner')
print(merged.head())
这里用了 join='inner',只保留两支股票都有数据的时间点。如果你想要保留所有时间点,可以用 join='outer',但要注意处理缺失值。
注意: A股集合竞价阶段(09:15-09:25)的数据,Tushare 默认不返回。如果你需要这部分数据,需要单独设置参数。我建议普通策略直接忽略集合竞价,除非你做的是高频盘口策略。
3.3 处理复权因子
分钟数据的复权处理,比日线要复杂得多。为什么?因为分钟数据量太大,逐笔复权计算量惊人。
我个人习惯的做法是:先拿到日线复权因子,再应用到分钟数据上。
具体步骤:
- 获取股票的日线复权因子表
- 找到每个交易日对应的复权因子
- 将该交易日的所有分钟数据乘以对应的复权因子
代码实现:
# 获取复权因子
adj_factor = pro.adj_factor(ts_code='000001.SZ', start_date='20230101', end_date='20230131')
# 获取分钟数据
minute_data = pro.minute(ts_code='000001.SZ', start_date='20230104', end_date='20230104')
# 将分钟数据的trade_time转为日期
minute_data['trade_date'] = pd.to_datetime(minute_data['trade_time']).dt.date
# 合并复权因子
minute_data = minute_data.merge(adj_factor[['trade_date', 'adj_factor']], on='trade_date', how='left')
# 应用复权(前复权)
price_cols = ['open', 'high', 'low', 'close']
for col in price_cols:
minute_data[col + '_adj'] = minute_data[col] * minute_data['adj_factor']
print(minute_data[['trade_time', 'close', 'close_adj']].head())
核心要点: 复权因子是按日计算的,所以同一交易日内的所有分钟数据,复权因子是一样的。千万别逐分钟去算复权,那是在浪费CPU。
3.4 知识体系总览
下面这张图,是我整理的本章节知识结构。你可以把它当作一个检查清单,看看自己有没有遗漏什么。
避坑指南: 我曾经在回测时发现分钟数据有跳空,排查了半天才发现是复权因子没更新。股票分红送转后,复权因子会变,记得定期更新你的复权因子表。
好了,分钟数据这块就讲到这里。记住三个核心点:接口调用要按天循环、数据拼接要对齐时间、复权处理要批量应用。把这些基础打牢,后面做策略才不会翻车。