搜索正则表达式时忽略子节点

Posted

技术标签:

【中文标题】搜索正则表达式时忽略子节点【英文标题】:Ignore children nodes when searching for regular expression 【发布时间】:2019-07-01 12:55:24 【问题描述】:

我想用 BeautifulSoup 识别大文本文档中的分割点。因此,我制定了一个正则表达式来查找特定字符串出现的Tag。问题是,如果我正在搜索的字符串中还有其他格式/子节点,它就不起作用。

t1 = BeautifulSoup("<p class=\"p p8\"><strong>Question-And-Answer</strong></p>")

t2 = BeautifulSoup("<p class=\"p p8\"><strong>Question</strong>-<strong>And</strong>-<strong>Answer</strong></p>")

t1.find(text = re.compile("Question[s]*-And-Answer[s]*", re.IGNORECASE))
>>> 'Question-And-Answer'

t2.find(text = re.compile("Question[s]*-And-Answer[s]*", re.IGNORECASE))
>>> None

输出应该是p Tag 对象。

【问题讨论】:

不确定这是否有帮助,但如果你这样做re.match("Question[s]*-And-Answer[s]*", t2.text).group(),它会输出你想要的结果。但就像我说的,不确定这是否有助于您继续前进。 我下面的回答能解决问题吗?请告知仍然缺少或需要澄清的内容。 【参考方案1】:

您在这里遇到的问题是您要查找的文本在p 节点内被strong 标签分割,因此在.find 中使用text 参数的正则表达式搜索将不起作用,它这就是它在 BS 中的实现方式。

如果您知道文本位于 p 节点中,您可以在 .find 调用中使用 lambda 表达式并针对每个 ptext 属性运行正则表达式搜索标记以找到您需要的元素:

print(t2.find(lambda t: t.name == "p" and re.search(r'Questions*-And-Answers*', t.text)))
# => <p class="p p8"><strong>Question</strong>-<strong>And</strong>-<strong>Answer</strong></p>

请注意,[s] 与正则表达式中的 s 相同。

【讨论】:

这种方法的问题是,如果它包含所需的文本,它将匹配完整的 html。为澄清起见,请尝试使用&lt;html&gt;&lt;body&gt;&lt;p class="p p8"&gt;&lt;strong&gt;Question&lt;/strong&gt;-&lt;strong&gt;And&lt;/strong&gt;-&lt;strong&gt;Answer&lt;/strong&gt;&lt;/p&gt;&lt;/body&gt;&lt;/html&gt; 作为输入运行您的代码。 @KeyurPotdar 如果OP只想获取p这些文本的元素,那么可以通过添加t.name == "p"条件来解决。

以上是关于搜索正则表达式时忽略子节点的主要内容,如果未能解决你的问题,请参考以下文章

如何使用正则表达式搜索忽略 NSPredicate 的某些字符?

为啥在正则表达式中以某种方式忽略子后的第一个字符? [复制]

您将如何使用正则表达式来忽略包含特定子字符串的字符串?

JS正则表达式

如何忽略正则表达式主题字符串中的空格?

Java正则表达式忽略/注释掉正则表达式的一部分[重复]