首先,我是stackoverflow的新手,所以如果我有任何错误,我深表歉意。我将尽量不再犯这些错误。
所以问题是,我正在尝试使用正则表达式来拆分一个句子或一个具有以下格式的语料库:
outside <X TYPE='X1'> inside <X TYPE='X2'> inside </X> <X TYPE='X3'> inside </X> </X> outside.
外部和内部只是随机词(unicode); <X TYPE='X?'> </X>
是完整标签,其中可以包含标签。
我想要的结果应该是这样的:
["outside", "<X TYPE='X1'> inside <X TYPE='X2'> inside </X> <X TYPE='X3'> inside </X> </X>", "outside"]
这意味着我想用最大的标记来分隔句子(对不起,我的英语)。
我所做的所有尝试都只会导致按最小标签(最大标签内的标签)进行拆分。 有人可以告诉我一种实现此目标的方法吗?非常感谢。
答案 0 :(得分:2)
首先,正则表达式可能不是完成这项工作的最佳工具,并且使用适当的XML解析器库可能会获得更好,更可靠的结果。但是,对于您的情况,以下似乎可以解决问题:
>>> import re
>>> text = "outside <X TYPE='X1'> inside <X TYPE='X2'> inside </X> <X TYPE='X3'> inside </X> </X> outside."
>>> re.split(r"(<.+>)", text)
['outside ',
"<X TYPE='X1'> inside <X TYPE='X2'> inside </X> <X TYPE='X3'> inside </X> </X>",
' outside.']
这将re.split
<...>
中包含的最大字符串引起,并且由于捕获组(...)
而保留了该部分。请注意,这只是捕获分别在 first 和 last 标记之前和之后的文本,但是不是不一定是任何标记之外的文本! / p>
>>> text2 = "outside <X> inside </X> outside, too? <X> inside again </X> outside."
>>> re.split(r"(<.+>)", text2)
['outside ',
'<X> inside </X> outside, too? <X> inside again </X>',
' outside.']
相反,如果您要使用单个标签,只需将.+
更改为.+?
,以按最小的此类组划分即可。
>>> re.split(r"(<.+?>)", text)
['outside ', "<X TYPE='X1'>", ' inside ', "<X TYPE='X2'>", ' inside ', '</X>', ' ', "<X TYPE='X3'>", ' inside ', '</X>', ' ', '</X>', ' outside.']
然后您可以使用它来使用堆栈或简单的标记计数器在任何标记之外查找文本:
parts = re.split(r"(<.+?>)", text2)
for part in parts:
if part.startswith("<"):
tags += -1 if part.startswith("</") else +1
elif tags == 0:
print(part)