过滤字典遇TypeError,如何返回剔除过滤项的完整字典?
解决字典按timestamp过滤后保留原结构的问题
你用集合推导式报错是因为字典是不可哈希类型,集合的元素必须是可哈希的,所以不能直接把字典放进集合里。要保留原字典的键值对结构,得用字典推导式,而不是列表或集合推导式。
另外注意你原代码里的变量名timedelta和导入的timedelta类重名了,这会覆盖内置类,后续如果再调用timedelta会出问题,建议改个变量名,比如time_threshold。
基础解决方案
直接用字典推导式遍历原字典的键值对,筛选符合条件的条目:
from datetime import datetime, timedelta # 避免变量名覆盖内置类,改用time_threshold time_threshold = datetime.now() - timedelta(hours=6) delta_string = time_threshold.strftime("%Y/%m/%d %H:%M:%S") test_data = {'test1': {'timestamp': '2023/02/11 19:03:51.000'}, 'test2' : {'timestamp': '2023/02/11 19:03:51.000'}} # 字典推导式:保留原键和符合条件的值 test_data = {key: value for key, value in test_data.items() if value['timestamp'] > delta_string} print(test_data)
说明
- 用
test_data.items()直接遍历键值对,比单独遍历键再取值更简洁高效 - 字典推导式格式为
{键: 值 for 键, 值 in 原字典.items() if 筛选条件},生成的新字典和原结构完全一致,只保留符合timestamp条件的条目
更严谨的时间比较方案
你的timestamp字符串带毫秒(.000),而delta_string没有毫秒,字符串比较刚好能正常工作,但如果格式不一致(比如有的带毫秒有的不带),容易出错。更稳妥的方式是把两边的时间都转成datetime对象再比较:
from datetime import datetime, timedelta time_threshold = datetime.now() - timedelta(hours=6) # 定义包含毫秒的时间解析格式 time_format = "%Y/%m/%d %H:%M:%S.%f" test_data = {'test1': {'timestamp': '2023/02/11 19:03:51.000'}, 'test2' : {'timestamp': '2023/02/11 19:03:51.000'}} # 转成datetime对象进行时间比较 test_data = { key: value for key, value in test_data.items() if datetime.strptime(value['timestamp'], time_format) > time_threshold } print(test_data)
这种方式不受字符串格式细节影响,能准确判断时间先后顺序。
内容的提问来源于stack exchange,提问作者blackswan
相关产品推荐
相关产品推荐

