Perl拆分和正则表达式查询

时间:2019-01-13 08:37:32

标签: regex perl split

我有一行文字,例如

这“是”一个非常有趣的问题“可以”解决的测试

我正在尝试将其拆分,以便我的数组@goodtext包含引号中包含的许多字符串。 所以我的数组将包含以下内容:

$goodtext[0] is
$goodtext[1] of very interesting
$goodtext[2] that can

不幸的是,每行中引用的部分数量有所不同...

3 个答案:

答案 0 :(得分:5)

假设没有明显的嵌套

my @quoted = $string =~ /"([^"]+)"/g;

或者,如果您需要在收集它们时能够进行一些处理

my @quoted;    
while ($string =~ /"([^"]+)"/g) {      #" (stop faulty markup highlight)
    # ...
    push @quoted, $1;
}

请注意,尽管"仍会与之匹配,但我们仍需要结尾[^"]+。这样一来,引擎就将其消耗掉并越过它,因此"的下一个匹配确实是下一个打开的匹配。

如果引号“ 也可以“嵌套” ”,那么您需要Text::Balanced


顺便说一句,请注意列表和标量contexts/g修饰符的行为差异。

  • 在由list assignment(在第一个示例中为@quoted施加)的列表上下文中,匹配运算符使用/g修饰符返回所有捕获的列表,或所有匹配项(如果模式中没有捕获(没有括号))

  • 在标量上下文中,例如,当将其评估为while条件时,其与/g的行为更为复杂。匹配之后,下次运行regex时,它将继续从上一个匹配的位置(一个接一个)搜索字符串,从而遍历匹配。

    请注意,我们不需要为此循环(这是导致细微错误的细微原因)

    my $string = q(one simple string);
    
    $string =~ /(\w+)/g; 
    say $1;               #--> one
    
    $string =~ /(\w+)g;
    say $1;               #--> simple
    

    在两个正则表达式中都没有/g时,我们不会得到这种行为,而是两次都打印了one

请参见全局匹配 in perlretut,例如 \G断言 in perloppos

答案 1 :(得分:3)

使用Text::Balanced提取引用的子字符串的示例:

#!/usr/bin/perl
use warnings;
use strict;
use feature qw/say/;
use Text::Balanced qw/extract_multiple extract_delimited/;

my $test = q{This "is" a test "of very interesting" problems "that can" be solved};

sub just_quotes {
  extract_multiple $_[0], [ sub { extract_delimited $_[0], '"' } ], undef, 1;
}

say for just_quotes $test;

这将产生:

"is"
"of very interesting"
"that can"

答案 2 :(得分:1)

尝试一下。

$ a='This "is" a test "of very interesting" problems "that can" be solved'

$ echo $a | perl -lne ' @arr=$_=~/"(.+?)"/g; print join("\n",@arr) '
is
of very interesting
that can

$