Python 获取股票 PB、PE 历史数据:来源清单与注意事项
摘要:还在为找不到可靠的历史 PE/PB 数据而烦恼?本文为你梳理了 10 个免费获取 A 股、美股、港股历史估值数据的关键渠道(AKShare、Tushare Pro、yfinance、Kaggle 等),横向对比其数据覆盖、获取方式、免费程度与核心限制,并提供数据源选择流程图、常见误区避坑指南及数据质量验证代码,助你高效、精准地获取所需数据。## 获取 A 股、美股、港股的 PE、PB 历史数据(按交易日排列的时间序列),渠道并不复杂。本文整理了一份可直接使用的来源清单,帮你省去逐一搜索的时间。
你是否曾遇到过这样的困扰:想分析某只股票的估值历史,却发现在不同数据源查到的 PE(市盈率)数值大相径庭?有的显示动态 PE,有的给出静态 PE,还有的则是滚动 PE(TTM)。这种“口径不一致”的问题,往往比“找不到数据”更令人头疼。实际上,获取 A 股、美股、港股的历史 PE/PB 数据(按交易日排列的时间序列)渠道并不少,许多甚至是免费的,配合 Python 仅需几行代码即可调用。本文旨在为你整理一份清晰、可直接使用的来源清单,并重点揭示各渠道的计算口径与潜在限制,帮你省去逐一搜索和试错的时间,直达最合适的数据源。
以下按来源分类,逐条说明各渠道能提供什么数据、有哪些限制、是否需要付费,供你按需选择。
A 股免费易用数据来源:建议优先尝试
1. AKShare:免注册、免 token,pip 安装即可使用
- 链接:AKShare 股票数据文档
- 数据内容:接口
stock_a_indicator_lg可直接返回个股的历史 PE、PE-TTM、PB、股息率、总市值,按交易日排列;底层数据来自乐咕乐股网。另有接口stock_zh_valuation_baidu,支持选择近一年、三年、五年、十年或全部时间范围。 - 使用方式:在 Python 中执行
pip install akshare,随后几行代码即可拉取。免费开源,无需令牌。 - 注意事项:由于依赖第三方网站(乐咕乐股、百度),上游改版时接口可能暂时失效,建议关注库的更新。
- 配套资源:AKShare 数据字典 可查询全部金融数据接口,免费使用。
2. Tushare Pro:覆盖全市场逐日数据,设有积分门槛
- 链接:Tushare Pro 每日指标文档
- 数据内容:接口
daily_basic包含pe、pe_ttm、pb字段,覆盖全市场,按日提供。 - 注意事项(重要):需注册获取 token,并有积分门槛——文档标注至少需 2000 积分才可调用,5000 积分后无总量限制。单次最多返回约 6000 条,需循环获取。若使用免费额度拉取全市场完整历史,额度可能不足。
3. 乐咕乐股网:AKShare 的部分数据源头
- 链接:legulegu.com
- 数据内容:网页可直接查看 A 股个股及整体市场(上证、深证、创业板、科创板)的 PE/PB 历史走势,包含加权值与中位数。AKShare 获取的即为该站数据。
- 注意事项:网页可供查阅,商用许可请以官方页面为准。
4. AData:开源免费替代方案
- 链接:GitHub - 1nchaos/adata
- 数据内容:免费开源,融合多个数据源,主打行情、K 线、概念数据。估值字段(如 PE/PB)的覆盖情况请以仓库文档为准,建议先确认后再使用。
A 股研究级数据来源:口径统一、可引用
5. CSMAR(国泰安):学术级、口径统一,需机构订阅
- 链接:data.csmar.com
- 数据内容:A 股估值、财务面板数据,口径统一,适用于学术论文引用。
- 注意事项:通常需要高校或机构图书馆订阅,或按数据集申请购买;可使用 edu 邮箱注册并绑定机构。个人免费获取全样本基本不可行,具体以官方页面为准。
6. CnOpenData:含财务报表,可推算估值
- 链接:cnopendata.com 上市公司财务报表
- 数据内容:A 股上市公司财务报表、财务指标数据,可据此自行推算估值。
- 注意事项:多数数据集需按集申请,可能收费,具体免费范围以官方页面为准。
现成数据集与可复现代码:适合无需自行编程的场景
7. 百度飞桨 AI Studio · 开放数据集
- 链接:aistudio.baidu.com/datasetoverview
- 数据内容:提供上千个开放数据集,并附可直接运行的 notebook(如官方 LSTM 预测 A 股走势教程)。
- 注意事项:可在站内搜索“股票 / A 股 / 行情”等关键词;某个数据集是否确实包含历史 PE/PB,需逐一打开查看,具体许可以各数据集页面为准。
8. 和鲸社区(Heywhale)
- 链接:heywhale.com
- 数据内容:国内数据科学平台,提供数据集与可复现的实战项目。
- 注意:同样需在站内搜索确认是否包含历史估值的股票数据集;具体下载方式与许可条款以平台页面为准。
美股 / 港股 / 全球数据来源:免费但存在局限
9. yfinance:以当前快照为主,非历史序列
- 参考链接:algotrading101 yfinance 指南
- 数据内容:
stock.info中包含trailingPE(滚动 PE)、forwardPE(预期 PE)、priceToBook(市净率)等字段,覆盖美股、港股及全球市场。 - 关键注意事项:返回的多为当前时点快照,不直接提供历史 PE/PB 时间序列。如需历史数值,需自行通过“历史价格 × 股数 / 账面价值”反算,或按月循环抓取。此外接口稳定性一般,存在限流。免费。
10. Kaggle:现成 CSV 数据集,以美股居多
- US Stock Market Data:kaggle.com/datasets/mohammedobeidat/us-stock-market-data
- S&P 500 Companies with Financial Information:kaggle.com/datasets/franoisgeorgesjulien/s-and-p-500-companies-with-financial-information
- 数据内容:现成 CSV,含基本面与技术面数据,以美股为主。
- 注意事项:下载需要 Kaggle 账号。各数据集覆盖的年限、字段及是否包含历史 PE/PB 等指标,请在下载前逐一查看说明。
数据源选择决策流程图
为帮助您更直观地根据自身需求选择最合适的数据源,以下流程图展示了基于三个关键决策因素(市场类型、是否需要历史序列、是否愿意编码)的推荐路径:
流程图说明:
- 市场类型:首先确定您需要A股数据还是美股/港股/全球数据。
- 历史序列需求:判断是否需要按交易日排列的历史数据,还是仅需当前估值快照。
- 编码意愿:评估是否愿意编写Python代码调用API,还是更倾向于免编码的网页查看或现成数据集。
根据以上决策路径,您可以快速定位到最适合自身需求的数据源。
主要数据源对比
为帮助你快速选择合适的数据源,下表横向对比了四个常用来源在关键维度的差异:
| 维度 | AKShare | Tushare Pro | yfinance | Kaggle |
|---|---|---|---|---|
| 数据覆盖 | A 股(为主) | A 股(全市场) | 美股、港股、全球 | 美股(为主) |
| 获取方式 | API(Python 库) | API(需 token) | API(Python 库) | CSV 数据集下载 |
| 免费程度 | 完全免费 | 免费额度有限,需积分 | 完全免费 | 需 Kaggle 账号,数据集免费 |
| 历史序列支持 | 支持(按交易日) | 支持(按日) | 仅当前快照,需自行循环获取历史 | 支持(数据集已包含历史序列) |
| 主要限制 | 依赖第三方网站,接口可能失效 | 积分门槛高,免费额度可能不足 | 不直接提供历史估值序列,接口稳定性一般 | 以美股为主,A 股/港股覆盖少,字段需逐一确认 |
| 适合场景 | 快速获取 A 股历史估值 | 需要全市场、口径统一的逐日数据 | 获取当前估值或自行构建历史序列 | 直接使用现成 CSV,避免编码 |
说明:以上对比基于各来源公开文档及常见使用经验,具体细节(如字段覆盖、数据年限、调用限制)请以各自官方页面为准。
常见误区与注意事项
常见问题解答 (FAQ)
以下是读者在获取和使用历史 PE/PB 数据时可能遇到的几个典型问题及解答:
1. 如何选择 AKShare 和 Tushare Pro?
选择依据:
- AKShare:适合快速上手、零成本获取 A 股历史估值数据。无需注册、无需 token,
pip install akshare即可使用。但需注意其数据依赖第三方网站(如乐咕乐股网),接口可能因上游改版而暂时失效。 - Tushare Pro:适合需要全市场、口径统一、逐日数据的场景。数据质量相对稳定,但需要注册获取 token,且有积分门槛(至少 2000 积分可调用,5000 积分后无总量限制)。若免费额度不足,拉取全市场历史数据可能受限。
简单决策:若仅需快速验证或小范围分析,优先选 AKShare;若需长期、稳定、全市场的数据用于正式分析或产品,且愿意投入一定成本(积分),则考虑 Tushare Pro。
2. 从 yfinance 获取的 PE 是哪种口径?
yfinance 返回的 PE 字段主要为:
trailingPE:滚动市盈率(TTM),基于最近 12 个月(Trailing Twelve Months)的每股收益计算。forwardPE:预期市盈率,基于未来 12 个月的预测每股收益计算。
重要提醒:yfinance 不直接提供历史 PE 时间序列,上述字段均为当前时点的快照值。如需历史序列,需自行通过“历史价格 × 股数 / 账面价值”反算,或按月循环抓取 trailingPE 快照来构建。
3. 数据出现大量缺失日期怎么办?
若数据缺失率较高(如 >5%),建议按以下步骤处理:
- 确认原因:检查是否为节假日、停牌,或数据源本身的问题。
- 选择处理方式:
- 短期缺失(1-3天):可使用向前填充(
fillna(method='ffill'))。 - 长期缺失或趋势明显:考虑线性插值(
interpolate(method='linear'))或季节性插值。 - 重要分析节点:保留缺失标记(如用 -999 标记),在后续分析时排除这些日期。
- 短期缺失(1-3天):可使用向前填充(
- 评估数据源:若缺失率持续较高(如 >20%),需考虑更换或补充数据源,或联系数据提供方确认。
文中提供的 Python 代码示例已包含连续性检查和简单插值方法,可直接参考。
4. 不同来源的 PE 值差异很大,以哪个为准?
这是典型的“口径不一致”问题。差异可能源于:
- PE 类型不同:动态 PE、静态 PE、滚动 PE(TTM)的计算方式不同。
- 财务数据基准:是否包含亏损股(负 PE)、采用何种复权方式、是否剔除停牌股票等。
- 更新频率与计算时点:不同数据源的更新时间和计算时点可能存在差异。
处理建议:
- 统一口径:在合并使用多个来源前,务必确认各来源的 PE 计算口径,尽量选择同一类型(如都使用 TTM)进行比较。
- 以官方或权威来源为准:对于 A 股,若追求口径统一、可引用,可考虑 CSMAR 等学术级数据源(需机构订阅)。
- 交叉验证:选取同一股票、同一时间点的数据,对比多个来源。若某个来源的值持续偏离主流范围,需谨慎使用。
- 明确分析目的:若仅需观察趋势,相对值比绝对值更重要;若需精确估值,则应选择口径透明、计算方法文档齐全的来源。
5. 免费数据可以用于商业项目吗?
不一定。各数据源的使用许可(License)差异很大:
- AKShare、yfinance:开源免费,但通常禁止商用或要求遵守特定条款(如注明来源、限制分发)。务必查阅其官方许可说明。
- Tushare Pro:免费额度仅供个人学习,商用需购买积分或企业版。
- Kaggle、AI Studio、和鲸社区:数据集许可因上传者而异,需逐一查看数据集页面的 License 条款。
- CSMAR、CnOpenData:通常绑定机构权限,个人免费获取全样本基本不可行,商用需购买授权。
核心原则:切勿默认“免费即可随意商用”。在使用任何数据前,务必查阅其官方许可页面,确认是否允许商用、再分发,以及是否需要署名(Attribution)。
1. 口径不一致是最易出现的问题
PE 分为动态、静态、滚动(TTM)等口径,还需关注是否包含亏损股的负值、采用何种复权方式、是否剔除停牌股票。不同来源的计算方法不同,数值自然存在差异。在合并使用多个来源前,应先统一口径,否则会影响结论的可靠性。
2. 接口可能失效
依赖第三方网站的接口(如 AKShare),在上游网站改版后可能无法使用,建议持续关注相关库的更新。
3. 许可与商用范围
各数据集与网站的使用许可不尽相同,能否商用、能否再分发,应以各自官方页面为准,切勿默认“免费即可随意使用”。CSMAR、CnOpenData 等通常绑定机构权限。
4. 下载前确认字段
对于 Kaggle、AI Studio、和鲸等平台的数据集,应先确认其覆盖的年份范围及是否包含所需字段,避免下载后才发现缺少历史 PE/PB 数据。
5. 数据质量检查与验证
获取数据后,建议进行以下质量检查,以确保数据的可靠性和准确性:
-
检查数据连续性:确认时间序列是否存在缺失的交易日。对于日频数据,应检查日期是否连续,避免因节假日、停牌或数据源问题导致的断点。可使用 Python 的
pandas检查日期序列的连续性,并对缺失日期进行标记或插值处理。 -
识别异常值:重点关注 PE/PB 等估值指标的异常值。例如,PE 为负值(通常表示公司亏损)或极端大值(可能因股价剧烈波动或财务数据异常导致)。可通过统计方法(如 3σ 原则)或业务规则(如设定合理范围阈值)进行筛查,并结合公司基本面判断是否为真实异常。
-
对比不同来源:当有条件时,可选取同一股票在同一时间点的估值数据,对比 AKShare、Tushare Pro 等不同来源的结果。若差异显著,需进一步核查各来源的计算口径(如 PE 类型、复权方式、数据基准日等),以确定哪个来源更符合你的分析需求。
-
验证逻辑一致性:对于可自行计算的数据(如通过财务报表推算 PB),可将计算结果与数据源提供的值进行交叉验证。同时,检查同一来源内部不同指标间的逻辑关系(如总市值 = 股价 × 总股本)是否基本一致。
下面是一个具体的 Python 代码示例,演示如何对获取到的 PE/PB 时间序列数据进行连续性检查和异常值检测:
import pandas as pd
import numpy as np
# 假设 df 是从 AKShare、Tushare Pro 或 Kaggle 获取的 PE/PB 数据
# 示例数据格式:DataFrame 包含 'date'(日期)和 'pe'(市盈率)两列
# df = pd.read_csv('your_data.csv') # 或从 API 获取
def check_data_quality(df, date_col='date', pe_col='pe', pb_col='pb'):
"""
检查 PE/PB 时间序列数据的质量
参数:
df: pandas DataFrame,包含日期和估值数据
date_col: 日期列名
pe_col: PE 列名
pb_col: PB 列名(可选)
"""
print("=== 数据质量检查报告 ===\n")
# 1. 检查数据连续性(识别缺失交易日)
print("1. 数据连续性检查:")
df[date_col] = pd.to_datetime(df[date_col])
df = df.sort_values(date_col).reset_index(drop=True)
# 生成完整的交易日序列(假设为工作日)
full_date_range = pd.date_range(start=df[date_col].min(),
end=df[date_col].max(),
freq='B') # 'B' 表示工作日
missing_dates = full_date_range.difference(df[date_col])
if len(missing_dates) > 0:
print(f" 发现 {len(missing_dates)} 个缺失交易日:")
print(f" 最早缺失:{missing_dates.min().strftime('%Y-%m-%d')}")
print(f" 最晚缺失:{missing_dates.max().strftime('%Y-%m-%d')}")
print(f" 缺失率:{len(missing_dates)/len(full_date_range):.2%}")
# 处理建议:标记缺失日期
df['is_missing'] = df[date_col].isin(missing_dates)
print(" → 处理建议:已标记缺失日期,可根据需要向前填充或线性插值")
else:
print(" 数据连续,无缺失交易日 ✓")
# 2. 异常值检测
print("\n2. 异常值检测:")
if pe_col in df.columns:
pe_data = df[pe_col].dropna()
# 检测负值(通常表示公司亏损)
negative_pe = df[df[pe_col] < 0]
if len(negative_pe) > 0:
print(f" PE 负值记录:{len(negative_pe)} 条")
print(f" 占比:{len(negative_pe)/len(df):.2%}")
print(" → 注意:负 PE 通常表示公司亏损,需结合基本面分析判断是否合理")
# 检测极端大值(如 PE > 100)
extreme_pe = df[df[pe_col] > 100]
if len(extreme_pe) > 0:
print(f" PE > 100 的记录:{len(extreme_pe)} 条")
print(f" 示例日期:{extreme_pe[date_col].iloc[:3].dt.strftime('%Y-%m-%d').tolist() if len(extreme_pe) > 0 else []}")
print(" → 注意:极端高 PE 可能因股价剧烈波动或财务数据异常导致")
# 使用 IQR 方法检测异常值
Q1 = pe_data.quantile(0.25)
Q3 = pe_data.quantile(0.75)
IQR = Q3 - Q1
lower_bound = Q1 - 1.5 * IQR
upper_bound = Q3 + 1.5 * IQR
iqr_outliers = df[(df[pe_col] < lower_bound) | (df[pe_col] > upper_bound)]
if len(iqr_outliers) > 0:
print(f" IQR 方法检测到 {len(iqr_outliers)} 个 PE 异常值")
print(f" 异常值范围:{iqr_outliers[pe_col].min():.1f} ~ {iqr_outliers[pe_col].max():.1f}")
if pb_col in df.columns and pb_col in df.columns:
pb_data = df[pb_col].dropna()
# 检测负 PB(理论上不应出现)
negative_pb = df[df[pb_col] < 0]
if len(negative_pb) > 0:
print(f" PB 负值记录:{len(negative_pb)} 条(理论上 PB 不应为负)")
print(" → 警告:负 PB 可能表示数据错误,需重点核查")
# 3. 缺失值统计
print("\n3. 缺失值统计:")
missing_stats = df.isnull().sum()
for col in [pe_col, pb_col]:
if col in df.columns:
missing_count = missing_stats[col]
missing_pct = missing_count / len(df)
print(f" {col} 缺失值:{missing_count} 条 ({missing_pct:.2%})")
if missing_pct > 0.1:
print(f" → 注意:{col} 缺失率较高,可能影响分析结果")
# 4. 数据质量评分
print("\n4. 数据质量评分(0-10分,10分为最佳):")
# 连续性得分
continuity_score = 10 * (1 - len(missing_dates) / len(full_date_range)) if len(full_date_range) > 0 else 10
# 异常值得分
outlier_score = 10
if pe_col in df.columns:
pe_outlier_pct = len(iqr_outliers) / len(df) if 'iqr_outliers' in locals() else 0
outlier_score = 10 * (1 - min(pe_outlier_pct, 0.2) / 0.2) # 异常值占比超过20%得0分
# 缺失值得分
missing_score = 10
if pe_col in df.columns:
missing_pct = missing_stats[pe_col] / len(df)
missing_score = 10 * (1 - min(missing_pct, 0.3) / 0.3) # 缺失率超过30%得0分
overall_score = (continuity_score + outlier_score + missing_score) / 3
print(f" 连续性得分:{continuity_score:.1f}/10")
print(f" 异常值得分:{outlier_score:.1f}/10")
print(f" 完整性得分:{missing_score:.1f}/10")
print(f" 综合质量得分:{overall_score:.1f}/10")
return df
# 使用示例
# 假设已有数据框 df
# df_checked = check_data_quality(df, date_col='trade_date', pe_col='pe_ttm', pb_col='pb')
# 处理缺失日期的简单插值方法示例
def handle_missing_data(df, date_col='date', value_col='pe'):
"""处理缺失数据的简单示例"""
df = df.set_index(date_col)
# 方法1:向前填充(适用于短期缺失)
df_filled_ffill = df[value_col].fillna(method='ffill')
# 方法2:线性插值(适用于趋势平稳的数据)
df_filled_interp = df[value_col].interpolate(method='linear')
# 方法3:标记为特殊值
df['is_original'] = ~df[value_col].isna()
df[value_col] = df[value_col].fillna(-999) # 用-999标记缺失
return df.reset_index()
print("\n=== 处理建议 ===")
print("1. 对于缺失交易日:")
print(" - 短期缺失(1-3天):可使用向前填充(ffill)")
print(" - 长期缺失或趋势明显:考虑线性插值或季节性插值")
print(" - 重要分析节点:保留缺失标记,在分析时排除")
print("\n2. 对于异常值:")
print(" - PE 负值:结合公司财报判断是否为真实亏损")
print(" - PE > 100:检查是否为新上市公司或特殊行业")
print(" - 统计异常值:可视情况剔除或用中位数替代")
print("\n3. 对于缺失值:")
print(" - 缺失率 < 5%:可考虑插值处理")
print(" - 缺失率 > 20%:需评估数据源可靠性")
代码说明:
- 连续性检查:通过对比完整工作日序列与现有数据日期,识别缺失的交易日。
- 异常值检测:
- 识别 PE 负值(通常表示公司亏损)
- 识别极端大值(如 PE > 100)
- 使用 IQR(四分位距)方法统计异常值
- 缺失值统计:计算各字段的缺失比例。
- 质量评分:从连续性、异常值、完整性三个维度给出综合评分。
- 处理建议:针对不同问题提供具体的处理方案。
使用建议:
- 在实际应用中,可根据具体数据特点调整阈值(如 PE > 100 可调整为 PE > 50 或使用动态阈值)。
- 对于 PB 数据,可添加类似的异常值检测逻辑。
- 插值方法需根据数据特征选择,股价类数据慎用简单插值。
参考资料与扩展阅读
数据源官方文档与许可协议
本文提到的各数据源官方链接及重要许可信息如下,使用前请务必查阅最新条款:
| 数据源 | 官方文档/主页 | 许可协议/使用条款 |
|---|---|---|
| AKShare | AKShare 股票数据文档 | AKShare License (MIT) |
| Tushare Pro | Tushare Pro 每日指标文档 | Tushare Pro 用户协议(注意积分与商用限制) |
| 乐咕乐股网 | legulegu.com | 网站未明确公开许可,商用前请通过网站联系方式咨询 |
| AData | GitHub - 1nchaos/adata | AData License (Apache 2.0) |
| CSMAR(国泰安) | data.csmar.com | 需机构订阅,具体商用授权请咨询官方销售 |
| CnOpenData | cnopendata.com 上市公司财务报表 | 多数数据集需申请,许可条款以各数据集页面为准 |
| 百度飞桨 AI Studio | aistudio.baidu.com/datasetoverview | 各数据集许可不同,请查看具体数据集页面的 License 说明 |
| 和鲸社区(Heywhale) | heywhale.com | 数据集许可由上传者设定,下载前请确认 |
| yfinance | yfinance Python 库 | yfinance License (Apache 2.0) |
| Kaggle | Kaggle Datasets | 各数据集许可不同(常见有 CC0、CC BY-SA 等),请查看数据集页面的 License 标签 |
重要提示:上表中的许可信息基于各项目公开文档,可能随时间变化。在使用任何数据源前,务必访问其官方链接,仔细阅读最新的使用条款、许可协议(License)和隐私政策,特别是关于商用、再分发、署名(Attribution)的要求。
关于 PE/PB 指标计算与口径差异的权威文章
若想深入理解 PE/PB 等估值指标的计算方法、不同口径的差异及其影响,推荐阅读以下文章:
-
Investopedia: Price-to-Earnings (P/E) Ratio
- 链接: https://www.investopedia.com/terms/p/price-earningsratio.asp
- 说明: 权威金融百科,详细解释了市盈率(PE)的概念、计算方法(静态 PE、动态 PE、滚动 PE),并对比了各自的优缺点与适用场景。
-
中国证券报:市盈率计算口径详解
- 链接: http://www.cs.com.cn/(可通过站内搜索“市盈率 计算 口径”查找相关分析文章)
- 说明: 国内权威财经媒体,常刊发关于 A 股估值指标计算口径、监管规范及常见误解的深度分析,有助于理解国内数据的特殊性。
-
CFA Institute: Price-to-Book Ratio (P/B)
- 链接: https://www.cfainstitute.org/en/research/industry-research/price-to-book-ratio
- 说明: CFA 协会的专业解读,深入探讨市净率(PB)的计算、在不同行业中的应用以及其作为估值指标的局限性。
阅读建议:
- 理解 PE 类型(静态、动态、滚动 TTM)的区别是避免数据混淆的第一步。
- 关注 财务数据基准(如是否包含亏损公司、是否使用最新财报或预测数据)。
- 对于 A 股数据,还需留意 复权方式(前复权、后复权、不复权)对历史估值序列的影响。
更多推荐



所有评论(0)