fol*_*oof 7 python regex lxml beautifulsoup html-parsing
我正在尝试使用python和BeautifulSoup标记一个HTML文件(字面上用"mark"标签包装字符串).问题基本如下......
说我有我原来的html文档:
test = "<h1>oh hey</h1><div>here is some <b>SILLY</b> text</div>"
Run Code Online (Sandbox Code Playgroud)
我想对本文档中的字符串进行不区分大小写的搜索(忽略HTML)并将其包装在"mark"标记中.所以我想说我想在html中找到"这里有一些愚蠢的文字"(忽略粗体标签).我想把匹配的html包装在"mark"标签中.
例如,如果我想在测试中搜索"这里有一些愚蠢的文本" ,那么所需的输出是:
"<h1>oh hey</h1><div><mark>here is some <b>SILLY</b> text</mark></div>"
Run Code Online (Sandbox Code Playgroud)
有任何想法吗?如果使用lxml或正则表达式更合适,我也会对这些解决方案持开放态度.
>>> soup = bs4.BeautifulSoup(test)
>>> matches = soup.find_all(lambda x: x.text.lower() == 'here is some silly text'):
>>> for match in matches:
... match.wrap(soup.new_tag('mark'))
>>> soup
<html><body><h1>oh hey</h1><mark><div>here is some <b>SILLY</b> text</div></mark></body></html>
Run Code Online (Sandbox Code Playgroud)
我之所以必须通过一个函数作为name
对find_all
那个比较x.text.lower()
,而不是仅仅使用text
与比较函数的参数x.lower()
,是后者不会发现在某些情况下,你显然需要的内容.
wrap
在某些情况下,该功能可能无法正常工作.如果没有,则必须改为enumerate(matches)
设置matches[i] = match.wrap(soup.new_tag('mark'))
.(您无法使用replace_with
引用自身的新标记替换标记.)
另请注意,如果您的预期用例允许任何非ASCII字符串匹配'here is some silly text'
(或者如果您想扩展代码以处理非ASCII搜索字符串),则上面使用的代码lower()
可能不正确.你可能想要打电话str.casefold()
和/或locale.strxfrm(s)
和/或使用locale.strcoll(s, t)
而不是使用==
,但你必须了解你想要什么,以及如何让它来选择正确的答案.