Как я могу использовать Perl для извлечения нескольких строк здесь? - PullRequest
0 голосов
/ 27 июля 2011

У меня проблемы с сортировкой и извлечением нескольких строк текста. Вот мой код:

my $searched = $doc->content;
    if($searched =~ /MODIFIED files in Task $_[1] : (.*?) The/gs){
        print $1,"\n";
        $Modified = $1;

    }
    if($searched =~ m/COMPILED in Task $_[1] : (.*?) The/ms){
        $Compiled = $1;

    }
    if($searched =~ m/DELETED in Task $_[1] : (.*?) Comments/ms){
        $Deleted = $1;

    }

Вот пример текстового файла:

The following are the MODIFIED files in Task 50104 :

**Directory                Filename                Version
---------                --------                -------
Something                Something                .....
......                   ......                   .....
.......                  ........                 .....**

The following are the files to be COMPILED in Task 50104 :

**Directory                Filename
---------                --------
.........               .........**


The following are the files to be DELETED in Task 50104 :

**Directory                Filename
---------                --------**

Comments:
 Blah blah.......

Где текст между ** - это то, что я хочу извлечь. Извините за плохое форматирование

Ответы [ 3 ]

1 голос
/ 27 июля 2011

Оператор триггера на помощь!

Оператор триггера имеет две стороны, левую и правую. Как только левая сторона оценивается как истина, триггер остается верным, пока правая сторона не оценивается как истина.

use strict;
use warnings;

my $searched = $doc->content;

my %info;  #< Store in a hash >

open my $string, '<', \$searched or die $!;

{
    my ( $type, $content );

    while ( <$string> ) {  # Process $searched line-by-line

        if ( /(MODIFIED|COMPILED|DELETED)/ ) {

            $type = $1;
        }

        $content .= $_, next if /^Directory/ .. /^\s*$/ ;

        $content =~ s{\s+$}{}; # Don't need that trailing whitespace

        if ( defined $type && defined $content ) {

            $info{$type} = $content;  # Or push @{ $info{$type} }, $content;
            undef $type;
            undef $content;
        }
    }
}
1 голос
/ 27 июля 2011

Я не уверен, что ваш текст содержит пробелы вокруг : и до / Comments (на самом деле, мне кажется, что за : следует новая строка, а The предшествует новая строка, а не пробел) ; вместо использования:

if($searched =~ /MODIFIED files in Task $_[1] : (.*?) The/gs){

попробуйте использовать:

if($searched =~ /MODIFIED files in Task $_[1] :(.*?)The/gs){

Я также не думаю, что вам нужен переключатель / g или / m ...

Если это не сработает, я бы посоветовал уточнить ваше регулярное выражение поэтапно, т. Е. Сначала убедиться, что /MODIFIED files in Task $_[1] : соответствует :, а затем добавить остальные.

0 голосов
/ 27 июля 2011

Вот быстрый взлом (не проверено). Вместо того чтобы читать весь файл в строку, используйте его в построчном режиме:

$ script.pl inputfile.txt

my %data;
my $header;
while (<>) {
    next if /^\s*$/; # skip empty lines
    if (/^The following are /) { # header line
        if (/(MODIFIED|COMPILED|DELETED)/) {
            $header = $1;
        } else { die "Bad header: $_" }
    } else { # data line
        die "Header expected" unless (defined $header);
        $data{$header} .= $_;
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...