1

这段代码:

#!/bin/perl

BEGIN { $/ = undef; };
open (FILE,"file.txt") ||  die "Cannot open $FILE:$!";

while (<FILE>) {
    my @matches;

    if  ( m#SelectEditPolicy\.do\?policyID=[0-9]{1,4}.*?">(.*?)</a>#sg) {
        push (@matches,$1);
    }

    foreach $rec (@matches) {
        print "$rec\n";
    }
}   

针对这个文件:

>cat file.txt
SelectEditPolicy.do?policyID=2958')">
Test123  OLD</a>
SelectEditPolicy.do?policyID=6643')">
Test123 </a>

执行 file.pl 仅返回第一个匹配项。我已经阅读了尽可能多的帖子,但没有任何成功?

我究竟做错了什么?

4

1 回答 1

1

你做错了很多事情。突出的第一个是BEGIN { $/ = undef; };如果您想 slurp 文件,请设置$/ = undef在最小的适用范围内。此外,一旦您决定读取文件,就没有理由使用while循环假装逐行读取它。

其次,您似乎对 HTML 文件进行了一些预处理,以将其简化为可以应用正则表达式的形式。使用HTML::TokeParser::Simple 之类的东西会更轻松。

#!/usr/bin/env perl

use strict;
use warnings;

my $content = do { local $/; <DATA> };

my @matches = ($content =~ m{
        SelectEditPolicy\.do\?
        policyID=[0-9]{1,4}[^>]*?">
        ([^<]*?)
        </a>
}xsg );

print "$_\n" for @matches;

__DATA__
SelectEditPolicy.do?policyID=2958')">
Test123  OLD</a>
SelectEditPolicy.do?policyID=6643')">
Test123 </a>

输出:

Test123 旧

测试123

HTML::TokeParser::Simple与原始 HTML 一起使用,我可能做过这样的事情(未经测试):

#!/usr/bin/env perl

use strict;
use warnings;

use HTML::TokeParser::Simple;

my $parser = HTML::TokeParser::Simple->new(url => 'http://example.com/');

my @policies;

while (my $tag = $parser->get_tag('a')) {
    my $href = $tag->get_attr('href');
    next unless defined $href;
    next unless $href =~ /SelectEditPolicy\.do\?policyID=([0-9]{1,4})/;
    push @policies, { $1 => $parser->get_text('/a') };
}
于 2012-11-14T03:46:31.577 回答