如何用Python遍历文件夹中CSV对应列批量绘制直方图?
问题:合并多CSV文件同列数据绘制直方图
我需要编写Python脚本读取文件夹中所有.csv文件,每个文件包含94列。目标是将所有文件的第1列数据合并绘制一个直方图,第2列合并绘制第二个直方图……最终生成94个直方图。
但我当前的代码逻辑是逐个处理文件,为每个文件的每一列单独绘制直方图,代码如下:
dfs = [] for iteration, file in enumerate(files): _dfs = pd.read_csv(file) dfs.append(_dfs) print('Data is', round(100*((iteration+1)/len(files)), 0), '% loaded') #Prints how much data has been loaded so far. '''----------------------------------- Plotting Graphs -------------------------------------- ''' for i in range(len(dfs)): #loops through files for k in dfs[i]: #loops through column headers plt.hist(dfs[i][k], 25) plt.title(files[i][22:]) #uses filename as title plt.xlabel(dfs[i][k].name) #uses column header for x-label plt.ylabel('Frequency Density') plt.show()
请问如何修改脚本实现最初的需求?
解决方案
核心思路是按列维度遍历,而非按文件维度:先收集所有文件的同一列数据,合并后再绘制对应直方图,循环处理94列即可。以下提供两种实现方式:
方式1:合并所有DataFrame(适合文件体积较小的场景)
直接将所有读取的DataFrame合并为一个整体,同一列的数据会自动聚合,之后逐列绘制直方图:
import pandas as pd import matplotlib.pyplot as plt # 保留原有的文件读取逻辑 dfs = [] for iteration, file in enumerate(files): _dfs = pd.read_csv(file) dfs.append(_dfs) print('Data is', round(100*((iteration+1)/len(files)), 0), '% loaded') # 合并所有DataFrame(确保所有CSV文件的列名/列顺序一致) combined_df = pd.concat(dfs, ignore_index=True) # 遍历每一列,用合并后的数据绘制直方图 for col_name in combined_df.columns: column_data = combined_df[col_name] plt.hist(column_data, bins=25) plt.title(f'Combined Histogram - Column: {col_name}') plt.xlabel(col_name) plt.ylabel('Frequency Density') plt.show() plt.clf() # 清空画布,避免图表重叠
方式2:逐列收集数据(适合大文件场景,节省内存)
如果CSV文件体积较大,无需合并整个DataFrame,而是逐列遍历每个文件,收集对应列的数据后再绘制:
import pandas as pd import matplotlib.pyplot as plt # 保留原有的文件读取逻辑 dfs = [] for iteration, file in enumerate(files): _dfs = pd.read_csv(file) dfs.append(_dfs) print('Data is', round(100*((iteration+1)/len(files)), 0), '% loaded') # 以第一个文件的列名作为基准(确保所有文件列顺序一致) column_names = dfs[0].columns for col_name in column_names: all_col_data = [] # 遍历所有文件,收集当前列的数据 for df in dfs: # 可选:过滤空值,避免直方图出现异常 valid_data = df[col_name].dropna().tolist() all_col_data.extend(valid_data) # 绘制合并后的直方图 plt.hist(all_col_data, bins=25) plt.title(f'Combined Histogram - Column: {col_name}') plt.xlabel(col_name) plt.ylabel('Frequency Density') plt.show() plt.clf()
注意事项
- 确保所有CSV文件的列顺序或列名完全一致,否则会导致数据错位;如果列名不一致但顺序一致,可以改用列索引(
range(94))遍历。 - 若需要批量保存直方图而非手动查看,可将
plt.show()替换为plt.savefig(f'histogram_col_{col_name}.png')。
内容的提问来源于stack exchange,提问作者probablysid
相关产品推荐
相关产品推荐

