如何基于CSV随机样本匹配ID更新指定列并保存文件?
解决方案:根据抽样ID更新CSV的winner列
要实现你的需求,我们可以通过以下步骤完成:
- 读取原始CSV文件并将所有行转为字典列表,方便按列名操作
- 随机选取500行样本,提取这些样本的唯一ID存入集合(用于快速查找)
- 遍历原始CSV的每一行,检查其ID是否在抽样集合中,若是则更新winner列
- 将修改后的内容写入新的CSV文件
下面是完整的代码实现,包含详细注释:
import csv import random # 配置参数 INPUT_CSV = "Original.csv" OUTPUT_CSV = "Updated_Original.csv" SAMPLE_SIZE = 500 WINNER_VALUE = "Yes" # 抽样行的winner值,可自定义 NON_WINNER_VALUE = "No" # 非抽样行的winner值,若不需要修改可注释相关代码 def update_winner_based_on_sample(): # 1. 读取原始CSV文件,转为字典列表 with open(INPUT_CSV, mode='r', newline='', encoding='utf-8') as infile: reader = csv.DictReader(infile) rows = list(reader) # 检查样本数量是否超过总行数,避免报错 if len(rows) < SAMPLE_SIZE: print(f"注意:原始文件仅包含{len(rows)}行,已全部选取作为样本") sample_rows = rows else: # 2. 随机选取指定数量的样本行 sample_rows = random.sample(rows, SAMPLE_SIZE) # 提取样本行的ID,存入集合(集合查找效率远高于列表) sample_ids = {row['ID'] for row in sample_rows} # 3. 遍历所有行,更新winner列 for row in rows: if row['ID'] in sample_ids: row['winner'] = WINNER_VALUE else: # 若不需要修改非抽样行的winner值,可删除下面这行 row['winner'] = NON_WINNER_VALUE # 4. 将修改后的内容写入新CSV文件 with open(OUTPUT_CSV, mode='w', newline='', encoding='utf-8') as outfile: writer = csv.DictWriter(outfile, fieldnames=reader.fieldnames) writer.writeheader() # 写入表头 writer.writerows(rows) # 写入所有行 if __name__ == "__main__": update_winner_based_on_sample() print(f"处理完成,结果已保存至{OUTPUT_CSV}")
关键说明:
- 使用
csv.DictReader和csv.DictWriter可以直接通过列名(如row['ID']、row['winner'])操作数据,比按索引更直观且不易出错 - 将抽样ID存入集合
sample_ids,是因为集合的成员检查操作时间复杂度为O(1),远快于列表的O(n),处理大文件时效率更高 - 增加了样本数量的判断,避免当原始文件行数不足500时
random.sample抛出异常 - 你可以根据需求自定义
WINNER_VALUE和NON_WINNER_VALUE,如果不需要修改非抽样行的winner值,只需删除else分支的代码即可
内容的提问来源于stack exchange,提问作者Daniel Mercer
相关产品推荐
相关产品推荐

