使用Beautiful Soup提取指定文本遇TypeError,求解决方法
问题分析
你遇到的TypeError: unsupported operand type(s) for +: 'NoneType' and 'int'错误,根源在于两个关键误解:
- 混淆了Tag对象和字符串的方法:
soup.select("td strong")返回的是BeautifulSoup的Tag对象列表,而非字符串。你调用的x.find('<br/><br/>')是Tag类的方法——它的作用是查找子标签,而非字符串匹配,所以找不到名为<br/><br/>的标签时会返回None,和整数10相加自然触发类型错误。 - 手动解析HTML字符串不可靠:即使你把
Tag转成字符串处理,一旦遇到结构不一致的标签(比如没有<br/><br/>的情况),字符串截取逻辑也会失效。
正确解决方案:用BeautifulSoup API解析(推荐)
既然已经用了BeautifulSoup,就应该利用它的HTML导航能力来提取文本,避免手动截取字符串。根据你给出的标签结构,目标文本位于两个<br/>之后,这里提供两种可靠的实现方式:
方法1:通过标签导航定位目标文本
直接找到第二个<br/>标签,然后获取它的下一个兄弟节点(也就是目标文本):
from bs4 import BeautifulSoup soup = BeautifulSoup(page.content, 'html.parser') area = soup.select("td strong") clean_area = [] for strong_tag in area: # 获取当前<strong>下所有的<br/>标签 br_tags = strong_tag.find_all('br') # 确保存在至少两个<br/>标签 if len(br_tags) >= 2: # 第二个<br/>的下一个节点就是目标文本,去除首尾空白 target_text = br_tags[1].next_sibling.strip() clean_area.append(target_text) else: # 处理不符合结构的情况,可根据需求改为跳过或默认值 clean_area.append("")
方法2:通过文本分割提取
利用get_text()提取所有文本,再根据<br/><br/>对应的空白分隔符分割,取最后一段有效文本:
from bs4 import BeautifulSoup soup = BeautifulSoup(page.content, 'html.parser') area = soup.select("td strong") clean_area = [] for strong_tag in area: # 用换行符作为分隔符提取所有文本,再按两个换行分割 text_sections = strong_tag.get_text(separator='\n').split('\n\n') # 反向遍历找最后一段非空文本 for section in reversed(text_sections): cleaned = section.strip() if cleaned: clean_area.append(cleaned) break else: clean_area.append("")
为什么这两种方法更好?
- 鲁棒性更强:即使HTML结构有细微变化(比如
<br/>带有属性、标签间有空格),BeautifulSoup也能正确识别,不会像手动字符串截取那样失效。 - 可读性更高:代码逻辑清晰,别人一看就知道你是在提取
<br/><br/>之后的文本,而非靠魔法数字(比如+10)来截取。
内容的提问来源于stack exchange,提问作者Leehbi
相关产品推荐
相关产品推荐

