Beefy Boxes and Bandwidth Generously Provided by pair Networks
Just another Perl shrine
 
PerlMonks  

How to extract certain range of text and write into another file?

by annel (Novice)
on Oct 13, 2013 at 10:43 UTC ( #1058057=perlquestion: print w/ replies, xml ) Need Help??
annel has asked for the wisdom of the Perl Monks concerning the following question:

Hi all, I have updated code as following, I wish to extract part of the text and write into another file. The loop of the code do not stop at my selected range of text. It read until the final match line of word. Please advise me. Thanks. For example, I need to extract the $ NAME: sandy until $$.TO and then join with the contents inside $NAME: patrick which is start from G1 until $$SRU. Any idea?
Text: $ NAME : corry $$.Inc s d $$.Oc s $$.TO G1 ty n1 EE EE M T1 T2 $$SRU G2 n1 y OO OO M T3 T4 $$SRU .EON $ NAME : patrick $$.Inc c d $$.Oc c $$.TO G1 td n3 EE EE M T5 T6 $$SRU G2 n3 y OO OO M T7 T8 $$SRU .EON $ NAME : sandy $$.Inc k l $$.Oc l $$.TO G1 td n3 FF FF M R5 R6 $$SRU G2 n3 y OO OO N R7 R8 $$SRU .EON
Code: use strict; use warnings; open my $F1, '<', 'testing.txt' or die "failed $!"; open my $F2, '>', 'out.txt' or die "failed $!"; while (<$F1>) { if (/^\$ NAME : sandy/../\$.TO/) { print $F2 $_; } if (/^\$ NAME : patrick/../\$.EON/) { if(/^G1/../\$SRU){ s/G1/G1.G1o.n/g; print $F2 $_;} } } close $F1; close $F2;

Comment on How to extract certain range of text and write into another file?
Select or Download Code
Re: How to extract certain range of text and display it?
by Anonymous Monk on Oct 13, 2013 at 10:58 UTC
      Thanks for your suggestion. I read it and I have get rid of $word but still I can't get my output.
Re: How to extract certain range of text and display it?
by moritz (Cardinal) on Oct 13, 2013 at 11:09 UTC

    Your most obvious problem is that there is no occurrence of Corry in the test data, only corry. And no, the two are not the same.

    Another problem is that you use $1, but the regex before it doesn't use a capturing group that could fill $1.

    A third problem is that the iteration variable is $word, but the regexes match against $_, thus have no chance to succeed. I'm pretty sure you get an uninitialized... warning from that. Didn't you? Or did you just ignore it? (hint: never ignore the warning).

      Hi, the problems you have mentioned are totally correct. I have correct the occurrence of  corry and get rid of $word. I can't figure out what variable should I match the section text.

        I can't figure out what variable should I match the section text.

        post the new code

Re: How to extract certain range of text and display it?
by CountZero (Bishop) on Oct 13, 2013 at 12:25 UTC
    Tell Perl that your records are terminated by ".EON\n\n".
    use Modern::Perl; { local $/ = ".EON\n\n"; while ( my $record = <DATA> ) { say "I found: $record"; # ... now do something with $record ... } } __DATA__ $ NAME : corry $$.Inc s d $$.Oc s $$.TO G1 ty n1 EE EE M T1 T2 $$SRU G2 n1 y OO OO M T3 T4 $$SRU .EON $ NAME : patrick $$.Inc c d $$.Oc c $$.TO G1 td n3 EE EE M T5 T6 $$SRU G2 n3 y OO OO M T7 T8 $$SRU .EON

    CountZero

    A program should be light and agile, its subroutines connected like a string of pearls. The spirit and intent of the program should be retained throughout. There should be neither too little or too much, neither needless loops nor useless variables, neither lack of structure nor overwhelming rigidity." - The Tao of Programming, 4.1 - Geoffrey James

    My blog: Imperial Deltronics
      Hi, thanks for your response. I did it as following but nothing display of the output.
      use warnings; use strict; my $test; my @words; open(INFO,"<","testing.pl")||die"Can't open file:$!\n"; chomp (@words=<INFO>); close(INFO); local $/ = ".EOM\n\n"; while ( my $record = @words) { print $record; }
      Where did I make mistake?

        CountZero's suggestion is

        local $/ = ".EON\n\n";

        you simply have a typo:".EOM...

        CountZero's advice is more than just "setting $/". You have to
        1. define $/ before reading your file
        2. of course, spell your record separator correctly, as noted by jakeease
        3. change your logic accordingly, because a "record" now contains multiple lines (those belonging to one name)
Re: How to extract certain range of text and write into another file?
by hdb (Prior) on Oct 15, 2013 at 09:05 UTC

    I would recommend to first read all of your data into a datastructure, like a hash of hashrefs with the names as the keys and then process the data according to your logic:

    use strict; use warnings; use Data::Dumper; my @extract; while(<DATA>){ if /^\.EON/ or /^\s*$/; push @extract, {name => $1} and next if /^\$ NAME : (\w+)/; ${$extract[-1]}{$1} = $2 if /(\S+)\s*(.*)/; } my %result = map { delete $_->{name} => $_ } @extract; print Dumper \%result; __DATA__ $ NAME : corry $$.Inc s d $$.Oc s $$.TO G1 ty n1 EE EE M T1 T2 $$SRU G2 n1 y OO OO M T3 T4 $$SRU .EON $ NAME : patrick $$.Inc c d $$.Oc c $$.TO G1 td n3 EE EE M T5 T6 $$SRU G2 n3 y OO OO M T7 T8 $$SRU .EON $ NAME : sandy $$.Inc k l $$.Oc l $$.TO G1 td n3 FF FF M R5 R6 $$SRU G2 n3 y OO OO N R7 R8 $$SRU .EON

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://1058057]
Approved by moritz
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others contemplating the Monastery: (6)
As of 2014-12-20 14:34 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    Is guessing a good strategy for surviving in the IT business?





    Results (96 votes), past polls