如何将行数不等的DataFrame按列拼接为列多索引主DataFrame且避免大量NaN
问题原因
你遇到的大量NaN问题是pandas横向拼接的默认逻辑导致的:pd.concat(..., axis=1)会按行索引对齐数据,不同股票的交易笔数不同,行索引范围不一致,笔数更少的股票在超出自身行数的位置会自动填充NaN。
如果你的核心需求是通过股票代码快速调取对应交易数据,同时避免冗余空值,可按需选择以下三种方案:
方案1:字典存储(最优解,无任何空值)
如果不需要统一的大宽表,直接用字典存储各股票的DataFrame即可,调用逻辑和你原本的需求几乎一致:
trade_dict = {} file_list = ['3MINDIA.NS.csv', 'AARTIDRUGS.NS.csv', 'AARTIIND.NS.csv', 'AAVAS.NS.csv', 'ABB.NS.csv'] for file_name in file_list: # 提取股票代码 symbol = file_name.split('.')[0] # 此处替换为你自己读取处理trades DataFrame的逻辑 trades = pd.read_csv(file_name) trade_dict[symbol] = trades # 调用示例:直接获取3MINDIA的所有交易数据 print(trade_dict['3MINDIA'])
方案2:保留多级列索引宽表,取数时过滤空值
如果你确实需要将所有数据整合到一个带多级列索引的DataFrame中,可保留原拼接逻辑,取数时过滤全空行即可:
import pandas as pd result_df = pd.DataFrame() file_list = ['3MINDIA.NS.csv', 'AARTIDRUGS.NS.csv', 'AARTIIND.NS.csv', 'AAVAS.NS.csv', 'ABB.NS.csv'] for file_name in file_list: symbol = file_name.split('.')[0] # 替换为你自己的trades读取逻辑 trades = pd.read_csv(file_name) # 加多级列索引,逻辑和你原来一致 trades.columns = pd.MultiIndex.from_product([[symbol], trades.columns]) result_df = pd.concat([result_df, trades], axis=1) # 封装取数方法,自动过滤全空行 def get_stock_trades(df: pd.DataFrame, symbol: str) -> pd.DataFrame: return df[symbol].dropna(how='all').reset_index(drop=True) # 调用示例 print(get_stock_trades(result_df, '3MINDIA'))
方案3:纵向拼接构造多级索引表(适合批量统计)
如果需要对所有股票的交易做统一的批量计算(比如统计全市场平均收益率、胜率等),用纵向拼接的多级索引表更方便,完全无空值:
all_trades = [] file_list = ['3MINDIA.NS.csv', 'AARTIDRUGS.NS.csv', 'AARTIIND.NS.csv', 'AAVAS.NS.csv', 'ABB.NS.csv'] for file_name in file_list: symbol = file_name.split('.')[0] trades = pd.read_csv(file_name) # 新增股票代码列 trades['symbol'] = symbol all_trades.append(trades) # 合并后构造两级索引:第一级为股票代码,第二级为该股票的交易序号 result_df = pd.concat(all_trades, axis=0).set_index(['symbol', pd.concat(all_trades).groupby('symbol').cumcount()]) # 调用示例:获取3MINDIA的所有交易数据 print(result_df.loc['3MINDIA'])
内容的提问来源于stack exchange,提问作者Comp1810
相关产品推荐
相关产品推荐

