使用Python在同一个字符串中多次重复匹配()

时间:2011-03-16 02:57:24

标签: python regex

我有一个正则表达式来寻找:ABC:`hello`模式。这是代码。

format =r".*\:(.*)\:\`(.*)\`"
patt = re.compile(format, re.I|re.U)
m = patt.match(l.rstrip())
if m:
    ...

当模式在一行中出现一次时效果很好,但是有一个例子“:tagbox:`Verilog`:tagbox:`Multiply`:tagbox:`VHDL`”。它只找到最后一个。

如何找到所有三种模式?

修改

根据Paul Z的回答,我可以使用此代码

format = r"\:([^:]*)\:\`([^`]*)\`"
patt = re.compile(format, re.I|re.U)
for m in patt.finditer(l.rstrip()):
    tag, value = m.groups()  
    print tag, ":::", value

结果

tagbox ::: Verilog
tagbox ::: Multiply
tagbox ::: VHDL

3 个答案:

答案 0 :(得分:8)

是的,dcrosta建议查看re模块文档,这可能是一个好主意,但我打赌你真的想要finditer函数。试试这个:

format = r"\:(.*)\:\`(.*)\`"
patt = re.compile(format, re.I|re.U)
for m in patt.finditer(l.rstrip()):
    tag, value = m.groups()
    ....

您当前的解决方案总是找到最后一个解决方案,因为初始.*尽可能多地吃掉,同时仍保留有效匹配(最后一个)。顺便说一句,这也可能使你的程序比它需要的速度慢得多,因为.*首先尝试吃掉整个字符串,然后逐个字符地备份,因为剩下的表达式告诉它“太多了,回去吧”。使用finditer应该更高效。

答案 1 :(得分:2)

你看过the re module docs了吗?除了re.match(在字符串的开头显式搜索)之外,还有re.findall(查找模式的所有非重叠事件),以及方法match和{编译search的{​​1}},它们都接受开始和结束位置以限制正在考虑的字符串部分。另请参阅RegexObject,它返回由模式拆分的子字符串列表。根据您的输出方式,其中一个可能会有所帮助。

答案 2 :(得分:0)

re.findall 甚至更好的 regex.findall 可以在一行中为您完成:

import regex as re #or just import re
s = ":tagbox:`Verilog` :tagbox:`Multiply` :tagbox:`VHDL`"
format = r"\:([^:]*)\:\`([^`]*)\`"
re.findall(format,s)

结果是:

[('tagbox', 'Verilog'), ('tagbox', 'Multiply'), ('tagbox', 'VHDL')]