按条件拆分大型DataFrame及多CSV文件读取方法问询
嘿,这两个问题都是数据处理中非常实用的场景,我来一步步给你讲清楚怎么实现~
一、按规则拆分大DataFrame
咱们的核心需求是双重条件拆分:每段最多2000行,同时如果段内action列的累计和先达到5000,就立刻在该行拆分。具体实现思路是先计算累计和,然后循环找到每一段的结束位置,代码如下:
import pandas as pd import numpy as np # 替换成你实际的DataFrame(这里用随机数据模拟你的45万行数据) np.random.seed(42) df = pd.DataFrame({ 'number': range(453627), 'action': np.random.randint(0, 10, size=453627) }) # 先计算action列的全局累计和,方便后续判断 df['action_cumsum'] = df['action'].cumsum() # 初始化存储拆分结果的列表,以及当前段的起始索引 split_dfs = [] start_idx = 0 while start_idx < len(df): # 先算出行数限制的结束索引:从start_idx开始最多2000行 max_row_end = start_idx + 1999 # 如果已经到最后一段,直接取最后一行索引 if max_row_end >= len(df): max_row_end = len(df) - 1 # 计算当前段需要达到的累计和阈值:从start_idx开始累计5000 start_cumsum = df.loc[start_idx, 'action_cumsum'] if start_idx > 0 else 0 target_cumsum = start_cumsum + 5000 # 在当前段范围内,找到第一个累计和达到阈值的行索引 mask = (df.index >= start_idx) & (df.index <= max_row_end) & (df['action_cumsum'] >= target_cumsum) threshold_end = df[mask].index.min() # 确定实际的结束索引:如果找到了阈值点就用它,否则用行数限制的结束点 if pd.notna(threshold_end): end_idx = threshold_end else: end_idx = max_row_end # 拆分当前段,去掉临时的累计和列,加入结果列表 current_df = df.loc[start_idx:end_idx, ['number', 'action']].copy() split_dfs.append(current_df) # 更新起始索引,进入下一段循环 start_idx = end_idx + 1 # 可以验证下拆分结果,比如看前3段的行数和累计和 for i, sub_df in enumerate(split_dfs[:3]): print(f"第{i+1}段:行数{len(sub_df)},action累计和{sub_df['action'].sum()}")
关键细节说明:
- 为什么要计算相对累计和?因为全局累计和是从第一行开始的,而每一段的累计和需要从当前段的开头重新计算,所以用
target_cumsum = start_cumsum + 5000来确保判断的是当前段的累计值; - 循环终止条件是
start_idx < len(df),确保所有行都被拆分完毕; - 拆分后的子DataFrame都存在
split_dfs列表里,你可以按需遍历保存为文件或者做后续处理。
二、读取文件夹中多个CSV到独立DataFrame
这个需求用glob模块匹配文件,再用字典存储每个文件对应的DataFrame是最方便的——既避免了手动创建一堆变量的麻烦,又能通过文件名快速定位对应的数据集。代码如下:
import pandas as pd from glob import glob # 替换成你的CSV文件夹路径,记得末尾加斜杠 csv_folder_path = './your_csv_files/' # 匹配文件夹下所有CSV文件(支持通配符,比如'*_2024.csv'只匹配带2024后缀的文件) all_csv_files = glob(f"{csv_folder_path}*.csv") # 创建字典存储每个CSV的DataFrame,键是文件名(不带路径和后缀) df_collection = {} for file_path in all_csv_files: # 提取纯文件名作为键(比如 './data/user.csv' 会变成 'user') file_name = file_path.split('/')[-1].replace('.csv', '') # 读取CSV到DataFrame df = pd.read_csv(file_path) df_collection[file_name] = df # 访问单个DataFrame示例:如果有个文件叫sales_data.csv,就用 df_collection['sales_data'] # 遍历查看所有DataFrame的基本信息 for name, df in df_collection.items(): print(f"文件{name}:共{len(df)}行,{len(df.columns)}列")
额外小技巧:
- 如果CSV文件有特殊格式(比如分隔符不是逗号、有表头问题),可以在
pd.read_csv()里加参数,比如sep=';'、header=1; - 如果需要对所有CSV做统一预处理(比如缺失值填充、列名修改),直接在循环里添加处理逻辑即可。
内容的提问来源于stack exchange,提问作者ashraf khaled
相关产品推荐
相关产品推荐

