Python3中按resolution<4条件过滤PDB API返回JSON的方法
嵌套PDB JSON字典的条件过滤实现
你之前筛选没出结果,大概率是踩了两个嵌套结构的坑:
- 把
em_3d_reconstruction当成普通字典直接取resolution,但这个字段本质是列表包裹的字典结构,哪怕单个条目里只有1个重建结果,也得先取列表元素再拿属性,直接用字符串key索引会直接触发类型错误 - 没给缺失字段的无效条目做兜底,比如你示例最后那个不完整的
5A2Q条目,硬取嵌套字段会直接抛KeyError中断整个循环
基础兼容版过滤逻辑
这段代码自动跳过结构不完整的无效条目,适配你当前拿到的JSON结构:
# 从外层嵌套字典取出所有条目列表 entries = result_json["data"]["entries"] filtered_result = [] for entry in entries: # 跳过没有em_3d_reconstruction字段、或该字段为空列表的无效条目 if not entry.get("em_3d_reconstruction"): continue # 取重建分辨率值,默认给999兜底(代表分辨率极差、不满足筛选条件) resolution = entry["em_3d_reconstruction"][0].get("resolution", 999) # 筛选分辨率小于4的条目 if resolution < 4: filtered_result.append(entry)
按照你示例里的数据,这段代码最终会筛选出2个重复的4UG0条目,过滤掉两个4V6X条目和不完整的5A2Q条目。
可选:重复条目去重
你示例里存在完全重复的4UG0、4V6X条目,如果不需要重复结果,可以基于rcsb_id做去重处理:
seen_pdb_ids = set() unique_filtered = [] for entry in filtered_result: pdb_id = entry["rcsb_id"] if pdb_id not in seen_pdb_ids: seen_pdb_ids.add(pdb_id) unique_filtered.append(entry)
去重后最终只会保留1个rcsb_id=4UG0的符合条件条目。
简洁版列表推导式写法
逻辑和上面的兼容版完全一致,适合快速实现:
filtered_result = [ entry for entry in result_json["data"]["entries"] # 兼容空字段、缺失分辨率的异常情况 if entry.get("em_3d_reconstruction") and entry["em_3d_reconstruction"][0].get("resolution", 999) < 4 ]
多重建结果场景的适配
实际从PDB拉取数据时,单个条目有时会关联多组EM重建数据,此时不要写死取列表第0位的分辨率,可根据需求调整判断逻辑:
- 只要有一组重建结果分辨率<4就保留条目:用
any()遍历所有重建结果做判断 - 要求所有重建结果分辨率都<4才保留条目:把判断换成
all()即可
# 只要任意一组重建分辨率<4就保留的判断示例 for entry in entries: has_good_res = any( recon.get("resolution", 999) < 4 for recon in entry.get("em_3d_reconstruction", []) ) if has_good_res: filtered_result.append(entry)
内容的提问来源于stack exchange,提问作者justykat
相关产品推荐
相关产品推荐

