You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

pandas合并DataFrame与CSV去重报unhashable list错解决方法

问题原因

drop_duplicates抛出unhashable list错误和DataFrame是否由字典列表构造无关,核心原因是某列/某几列中存储了list类型的值:list是可变类型不可哈希,pandas去重时需要计算值的哈希值做比对,遇到list就会触发该报错。
这类问题基本都是API返回的嵌套字段(比如对局掉落道具列表、对局参与玩家ID列表等)未做序列化处理,直接以原始list结构存入DataFrame导致的。

实现方案
  • 先预处理所有包含list的列,将list转为可哈希的元组或字符串,从根源解决哈希报错。如果后续需要解析嵌套结构就转元组,不需要保留结构直接转字符串即可。
  • 去重优先使用数据自带的唯一标识字段(比如对局ID、记录流水号)作为比对依据,比全字段比对效率高,也不会因为浮点精度、字段值微小偏差导致去重失效。没有唯一标识时再走全字段去重。
  • 首次运行时目标CSV不存在,直接写入首批拉取的100条数据即可;后续运行只追加历史数据中不存在的新条目,不需要每次全量重写文件,IO性能更好。
参考代码
import pandas as pd
import os

SAVE_PATH = 'StatTracker.csv'

# 加载本次拉取的新批次数据
df_new = pd.DataFrame(statsTableList)

# 预处理含list的列,解决不可哈希报错
for col in df_new.columns:
    if df_new[col].apply(lambda x: isinstance(x, list)).any():
        # 需要保留嵌套结构转tuple即可,不需要直接用str()转字符串
        df_new[col] = df_new[col].apply(tuple)

# 首次运行直接写入初始数据
if not os.path.exists(SAVE_PATH):
    df_new.to_csv(SAVE_PATH, index=False)
else:
    # 读取历史存储数据
    df_history = pd.read_csv(SAVE_PATH)
    # 同步新数据格式:CSV读入的序列化元组会自动转字符串,要和历史格式对齐才能准确去重
    for col in df_new.columns:
        if df_new[col].apply(lambda x: isinstance(x, tuple)).any():
            df_new[col] = df_new[col].apply(str)
    
    # 有唯一主键就把主键列名传给subset参数,比如subset=['match_id'],无主键则去掉subset走全字段匹配
    df_append = df_new[~df_new.isin(df_history.to_dict('list')).all(axis=1)]
    
    # 追加写入新数据,不重复写表头、不写入索引
    df_append.to_csv(SAVE_PATH, mode='a', header=False, index=False)

注意:如果习惯用concat+drop_duplicates的写法,只要完成上述列类型预处理,原有写法就可以正常运行,不会再触发unhashable报错,两种去重逻辑最终效果一致。

内容的提问来源于stack exchange,提问作者Skye Peterson

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.26 21:24:29