在Google Colab中用Python提取金融数据的优化方案咨询
优化yfinance金融数据提取的运行效率
原代码运行缓慢主要有几个核心问题,直接给你拆解和优化方案:
原代码的低效点
- 重复创建Ticker实例:每次循环都两次调用
yf.Ticker(stock),每次都会发起网络请求,完全属于冗余操作 - 频繁使用
df.append():pandas的append是逐行拼接,每次都会生成新的DataFrame,循环次数越多,性能损耗越严重 - 冗余导入:导入了一堆未用到的库(比如matplotlib、requests、pandas_datareader),占用内存且无意义
- 逻辑偏差:原代码每个日期获取的都是当前最新的财务数据,而非对应日期的历史数据——如果你的需求是获取每个月末的历史指标,原逻辑其实不成立
优化后的代码(保留原逻辑,仅提升效率)
import pandas as pd import yfinance as yf from datetime import datetime stocks = ['AYX', 'TEAM', 'DDOG', 'MDB', 'TDC', 'CFLT'] start_date = '2021-10-1' current_date = datetime.now().strftime("%Y-%m-%d") date_range = pd.date_range(start=start_date, end=current_date, freq='M') dates = [date.strftime("%Y-%m-%d") for date in date_range] # 用列表收集所有数据,最后一次性生成DataFrame,避免频繁拼接的性能损耗 data_list = [] for stock in stocks: # 只创建一次Ticker实例,复用它的所有数据接口 ticker = yf.Ticker(stock) info = ticker.info fast_info = ticker.fast_info net_debt = info['totalDebt'] - info['totalCash'] market_cap = fast_info['market_cap'] # 每个日期复用当前最新数据(匹配原代码逻辑) for date in dates: data_list.append({ 'Date': date, 'Stock': stock, 'NetDebt': net_debt, 'marketcap': market_cap, 'EV': market_cap + net_debt }) # 一次性生成DataFrame,效率比循环append高数十倍 df = pd.DataFrame(data_list) print(df)
额外修正:获取对应日期的历史财务数据
如果你的真实需求是获取每个月末当时的NetDebt和市值(而非当前最新数据),上面的代码还需要调整,因为yfinance的info返回的是实时数据。可以通过以下方式获取历史资产负债表与市值数据:
import pandas as pd import yfinance as yf from datetime import datetime stocks = ['AYX', 'TEAM', 'DDOG', 'MDB', 'TDC', 'CFLT'] start_date = '2021-10-1' current_date = datetime.now().strftime("%Y-%m-%d") date_range = pd.date_range(start=start_date, end=current_date, freq='M') data_list = [] for stock in stocks: ticker = yf.Ticker(stock) # 获取历史资产负债表(季度维度),转置后日期为行索引 balance_sheet = ticker.balance_sheet.T # 获取每日市值历史数据 hist_market_cap = ticker.history(start=start_date, end=current_date)['MarketCap'] for date in date_range: # 找到目标日期之前最近的资产负债表数据 bs_date = balance_sheet.index[balance_sheet.index <= date].max() total_debt = balance_sheet.loc[bs_date, 'Total Debt'] total_cash = balance_sheet.loc[bs_date, 'Cash And Cash Equivalents'] net_debt = total_debt - total_cash # 找到目标日期对应的市值(无数据则取最近日期) mc_date = hist_market_cap.index[hist_market_cap.index <= date].max() market_cap = hist_market_cap.loc[mc_date] data_list.append({ 'Date': date.strftime("%Y-%m-%d"), 'Stock': stock, 'NetDebt': net_debt, 'marketcap': market_cap, 'EV': market_cap + net_debt }) df = pd.DataFrame(data_list) print(df)
其他提速技巧
- 在Google Colab中切换到GPU/TPU运行时:对网络请求为主的代码提升有限,但能加快pandas的运算速度
- 多线程批量请求:如果股票数量较多,可以用
concurrent.futures实现多线程请求,注意不要触发yfinance的请求频率限制
内容的提问来源于stack exchange,提问作者Aman Jain
相关产品推荐
相关产品推荐

