Perl:如何使用正确的数据结构:multili line,多个捕获组

时间:2012-11-21 04:39:24

标签: regex perl

我有一个文件:

XXGuy:Tom1XXBill1XX<tab>XXBlah2XX\n
XXFriend:Bob1XXcarry:Stuff1XX\n
XXGuy:Tom2XXBill2XX<tab>XXBlah7XX\n
XXFriend:Bob2XXcarry:Stuff2XX\n

我要提取的内容是Tom {1,2},Bob1 {1,2}和Stuff1 {1,2}并打印:

“Tomx的朋友是Bobx并且正在携带Stuffx”

我可以使用具有多个捕获组的多行正则表达式,Tomx,Bobx和Stuffx将分别为1美元,2美元和3美元,我可以打印出每个元素,但不能按照我的方式处理它们如上所述 - 我不知道如何存储到什么结构(数组/哈希看不到这里的账单?)并检索数据。

我正在看这些帖子:

Perl: Pulling pairs of values from an array Finding multiple matches with multiline regex perl

建议?

2 个答案:

答案 0 :(得分:2)

通常,您在列表上下文中查找/g标志,但您对结果的处理仍然是更难的部分。我会做这样的事情,我不确定它是绝对最好的方式,但它应该起作用:

#!/usr/bin/env perl

use strict;
use warnings;

my $string = <<'END';
XXGuy:Tom1XXBill1XX XXBlah2XX
XXFriend:Bob1XXcarry:Stuff1XX
XXGuy:Tom2XXBill2XX XXBlah7XX
XXFriend:Bob2XXcarry:Stuff2XX
END

my @data;
push @data, [$1,$2,$3] while $string =~ /(Tom\d+).*?(Bob\d+).*?(Stuff\d+)/msg;

use Data::Dumper;
print Dumper \@data;

perldoc perlretutperldoc perlreref(或天堂帮助你perldoc perlre)中阅读更多内容

答案 1 :(得分:0)

这是一个使用数据命名捕获的选项:

use strict;
use warnings;

while (<DATA>) {
    if (/:(?<name>.+?)XX.+(?=\t)/) {
        print "$+{name}'s friend is ";
        next;
    }

    /:(?<name>.+?)XX.+:(?<stuff>.+?)XX/;
    print "$+{name} and is carrying $+{stuff}\n";
}

__DATA__
XXGuy:Tom1XXBill1XX XXBlah2XX
XXFriend:Bob1XXcarry:Stuff1XX
XXGuy:Tom2XXBill2XX XXBlah7XX
XXFriend:Bob2XXcarry:Stuff2XX

输出:

Tom1's friend is Bob1 and is carrying Stuff1
Tom2's friend is Bob2 and is carrying Stuff2