是否有Perl相当于Python的re.findall / re.finditer(迭代正则表达式结果)?

时间:2009-01-22 01:52:54

标签: python regex perl iterator

在Python编译的正则表达式模式have a findall method中执行以下操作:

  

返回所有非重叠的匹配项   字符串中的模式,作为列表   字符串。扫描字符串   从左到右,比赛是   按顺序返回。如果一个或   更多的团体出现在   模式,返回组列表;这个   将是一个元组列表,如果   模式有多个组。空   匹配包含在结果中   除非他们触及开头   另一场比赛。

在Perl中执行此操作的规范方法是什么?我能想到的一个天真的算法是“当搜索并用空字符串替换成功时,做[套件]”。我希望有一个更好的方式。 : - )

提前致谢!

3 个答案:

答案 0 :(得分:13)

在匹配中使用/g修饰符。来自perlop手册:

  

/g”修饰符指定全局模式匹配 - 即在字符串中尽可能多地匹配。它的行为取决于上下文。在列表上下文中,它返回正则表达式中任何捕获括号匹配的子字符串列表。如果没有括号,则返回所有匹配字符串的列表,就好像整个模式周围有圆括号一样。

     

在标量上下文中,“m//g”的每次执行都会找到下一个匹配项,如果匹配则返回true,如果没有进一步匹配则返回false。可以使用pos()函数读取或设置最后一次匹配后的位置;请参阅pos中的“perlfunc”。匹配失败通常会将搜索位置重置为字符串的开头,但您可以通过添加“/c”修饰符(例如“m//gc”)来避免这种情况。修改目标字符串也会重置搜索位置。

答案 1 :(得分:7)

基于Chris的回应,将//g正则表达式包含在while循环中可能最相关,例如:

my @matches;
while ( 'foobarbaz' =~ m/([aeiou])/g )
{
    push @matches, $1;
}

粘贴一些快速的Python I / O:

>>> import re
>>> re.findall(r'([aeiou])([nrs])','I had a sandwich for lunch')
[('a', 'n'), ('o', 'r'), ('u', 'n')]

为了在Perl中获得类似的东西,构造可能是这样的:

my $matches = [];
while ( 'I had a sandwich for lunch' =~ m/([aeiou])([nrs])/g )
{
    push @$matches, [$1,$2];
}

但总的来说,无论你要迭代什么函数,你都可以在while循环中进行。

答案 2 :(得分:2)

很好的初学者参考,其内容与@kyle的答案相似:Perl Tutorial: Using regular expressions