sam
sam

Reputation: 83

Matching data using Regular Expressions in perl

In a perl file some text is there and I want to do pattern match. But it is not working?

Example:

    open( FH, "perll.txt" );
    while (<FH>) {  $Return .= $_; }
    close(FH);
    if($Return =~ /Session Id.*\:\s.*\-\w+/)
    {
       print "data si$1";
        push(@se,$1);
        next;
        print "yyyyyy@se";
    }

perll.txt

    Session Id             : fffffa800d461010-1
          this is a good language
    Session Id             : fffffa800d461010-0990wew

Output I need is:

    fffffa800d461010-1,fffffa800d461010-0990wew   in an array

Upvotes: 0

Views: 87

Answers (3)

Gowtham Ganesh
Gowtham Ganesh

Reputation: 340

It doesnt work because,

1) you're trying to copy the entire text in the file to the scalar $Return and then trying to parse the scalar variable ( which is not the right thing to do ).

Better approach is to parse the file line-by-line and when there is a match it should be pushed to the array.

2) And, in the pattern matching there is no pattern to catch (you havent specified which pattern needs to be matched or in other words, what is $1? ). That needs to be corrected.

#!/usr/bin/perl

my $Return;
my @se;
open( FH, "hello.txt" );
while (<FH>) {
  $Return = $_;

    if($Return =~ /Session Id\s+:\s+(.*)/)
    {

       push(@se,$1);
    }
}
my $output = join(",",@se);
print $output;
close(FH);

Upvotes: 1

Sobrique
Sobrique

Reputation: 53498

OK, first off - rule 1 of perl troubleshooting. Turn on use strict; and use warnings;.

Second: while (<FH>) { $Return .= $_; } - you're reading the whole file into $Return. OK, if that's what you actually mean. But I don't think you need to. It's probably also better written as local $/; $return = <FH>.

Thirdly: Please use a 3 argument open with lexical filehandles. 2 Arg has been deprecated quite some time, and that style of FH is a global variable, which is just bad form.

Fourth: Your regular expression doesn't capture anything in it's match - so $1 will always be empty.

Fifth: Your regular expression doesn't have a g flag, so it only matches once against your whole file block of text.

This should do what you want:

#!/usr/bin/perl

use strict;
use warnings;

open( my $input, "<", "perll.txt" ) or die $!;

my @session_ids;
while ( <$input> ) {
    my ( $session_id )= m/Session Id\s+:\s*(\S+)/;
    push ( @session_ids, $session_id ) if $session_id; 
}
close ( $input );
print join ( ",", @session_ids );
  • We open your file as $input.
  • iterate it, matching Session Id and capturing the id with (\S+) (one or more non-spaces) into $session_id. (Note - needs to be a list context for this to work.
  • If $session_id is present, we insert it into @session_ids.

Note that it does this without needing to read your whole file into memory, which is generally a good thing to avoid unless necessary. (And it doesn't seem to be in your scenario).

Upvotes: 1

sandeep
sandeep

Reputation: 152

Try this

undef $/;
open (FH,"1.txt");
my $string = <FH>;
close(FH);

@arr = $string =~ /Session Id\s+?:\s+?(.*?)\n/isg;

print "@arr\n";

Upvotes: -1

Related Questions