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

Python3中替换has_key方法:解决Python2兼容的标签属性判断问题

解决方案

没问题,我来帮你搞定Python2到Python3的适配,还有标签筛选的问题!

1. 适配Python3的判断逻辑

Python3里已经移除了字典的has_key()方法,对于BeautifulSoup的Tag对象,最优雅的方式是用它自带的has_attr()方法(这个方法在Python2和3中都兼容,可读性也更强)。修改后的函数如下:

def has_class_but_no_id(tag):
    # 检查标签是否有class属性,同时没有id属性
    return tag.has_attr('class') and not tag.has_attr('id')

如果你更习惯直接操作属性字典,也可以写成这样(效果完全一致):

def has_class_but_no_id(tag):
    return 'class' in tag.attrs and 'id' not in tag.attrs

2. 从descendants列表中筛选符合条件的标签

需要注意的是,soup.descendants返回的迭代器包含所有类型的节点(比如文本节点、注释节点,甚至空白符),这些非标签节点没有属性,直接判断会报错。所以我们需要先过滤出Tag类型的元素,再应用判断条件。

方法一:基于你已有的list_of_descendants列表

先导入BeautifulSoup的Tag类,然后用列表推导式筛选:

from bs4 import Tag

filtered_tags = [
    tag 
    for tag in list_of_descendants 
    if isinstance(tag, Tag) and has_class_but_no_id(tag)
]

方法二:直接从soup.descendants迭代筛选(更高效)

如果不需要提前把所有节点存到列表里,直接迭代筛选可以节省内存,代码更简洁:

from bs4 import Tag

filtered_tags = [
    tag 
    for tag in soup.descendants 
    if isinstance(tag, Tag) and tag.has_attr('class') and not tag.has_attr('id')
]

这种方式连单独的函数都可以省略,直接把判断逻辑写在推导式里。

验证结果

你可以通过打印filtered_tags来查看筛选出的标签,或者遍历它们获取具体内容:

for tag in filtered_tags:
    print(tag.name, tag.get('class'))  # 打印标签名和class属性值

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.22 08:14:58