SPUG: multiline matching question
John W. Krahn
krahnj at telus.net
Thu Sep 8 19:18:51 PDT 2005
Richard Wood wrote:
> SPUGsters,
>
> I am trying to efficiently grab sets of data from
> multiple lines of a file and print the collected data
> out on one line per set. I've never tried multi line
> matching before ( I usually just write a program that
> tests which kind of line I am processing). But I
> believe that this can be done in one match statement.
> So I would like some help. Currently, in the test
> file that I am including, I am getting the data from
> the second set of lines which seems pretty unusual to
> me. I'm looking forward to understanding what I am
> doing wrong.
>
> The file consists of 150 character records. Every
> third record starts a new set of data. I need bits
> and pieces from records 1 & 2 of each set.
>
> here is the command line that I am using:
>
> $ perl -wne 'undef
> $/;/(AP01).{5}(..)..(\d\d\d).{38}(.{19}).{9}(.{5}).{64}(.{80})/gs
> and print "$1 $2 $3 $4 $5 $6\n";' sample.txt
$ perl -MO=Deparse -wne 'undef
$/;/(AP01).{5}(..)..(\d\d\d).{38}(.{19}).{9}(.{5}).{64}(.{80})/gs
and print "$1 $2 $3 $4 $5 $6\n";' sample.txt
BEGIN { $^W = 1; }
LINE: while (defined($_ = <ARGV>)) {
undef $/;
print "$1 $2 $3 $4 $5 $6\n" if
/(AP01).{5}(..)..(\d\d\d).{38}(.{19}).{9}(.{5}).{64}(.{80})/gs;
}
-e syntax OK
You are undefining the input record separator after the program has read the
first line so you need to either undefine it in a BEGIN block or with a
command line switch:
perl -ne'BEGIN{undef $/}...'
Or:
perl -0777ne'...'
Your expression '//gs and print ""' will only execute once. You need to loop
over each match like:
perl -0777ne'print "$1 $2 $3 $4 $5 $6\n" while
/^(AP01).{5}(..)..(\d\d\d).{38}(.{19}).{9}(.{5}).{64}(.{80})/gms' sample.txt
Another way to do it:
perl -F'\n\s+\n' -0777ane'/^AP01/ and print join " ", unpack(
"a4x5a2x2a3x38a19x9a5x64a80", $_ ), "\n" for @F' sample.txt
John
--
use Perl;
program
fulfillment
More information about the spug-list
mailing list