justkar4u has asked for the wisdom of the Perl Monks concerning the following question:

Hi, I am a newbie to perl. I am trying to pass the filename and search for a keyword in that file and if found print that line else print not found message. However though my file has the keyword I get not found message.Please help.I know its pretty straightforward but I am stuck with this for hours :(...If i use foreach then I get multiple not found print messages for all the lines that dont have the criteria..what do I do ?
#!/usr/bin/perl # main program; print "Enter the filename to be parsed\n"; my $file = <STDIN>; open (FILE,$file); @lines = <FILE>; close (FILE); print "Enter the keyword to be searched in the file\n"; chop (my $key = <STDIN>); if (grep {$_ eq $key} @lines) # Search for the key pattern in +the file information. { print "$_ \n"; # If found print the line } else { print "Keyword not found\n"; }

Replies are listed 'Best First'.
Re: Error using grep
by GrandFather (Saint) on Mar 29, 2011 at 00:43 UTC

    The following sample may or may not fix your immediate problem (you've not given enough information for me to be able to tell), but it will avoid a whole slew of problems in the future:

    #!/usr/bin/perl use strict; use warnings; print "Enter the filename to be parsed\n"; my $fileName = <STDIN>; print "Enter the keyword to be searched in the file\n"; my $keyword = <STDIN>; chomp $fileName; chomp $keyword; open my $inFile, '<', $fileName or die "Failed to open $fileName: $!\n +"; # Search for the key pattern in the file information. while (defined (my $line = <$inFile>)) { chomp $line; next if $line ne $keyword; print "Found key word $keyword on line $.\n"; exit; } print "Keyword not found\n";

    Always use strictures (use strict; use warnings;).

    Always use three parameter open, lexical file handles (using my) and check the result from open.

    Use chomp not (ever) chop.

    Don't slurp files into an array - use a while loop instead.

    Note that this may no work for you because it expects to match the entire line against the key word. If you just want to see if the line contains the key word then use the regular expression $line =~ /\Q$keyword\E/ or the expression 0 <= index $line, $keyword (although there are problems with both of these test too, depending on what you actually want to match).

    True laziness is hard work
      Hi, Sorry for not being clear earlier. I do want to search for any keyword(mostly alphabetical words) and if present in that line , I need to display the entire line.Line may have spaces or special characters. I do not know how to use the boundary conditions. I tried using {/\b\Q$key\E\b/} or outside the {\b/\Q$key\E/\b} but either of them dint work. I also read about using /p to preserve the prematch ,match and post match expressions but I got this error :Illegal division by zero at ./test1.pl line 14, <STDIN> line 2. for entering zmm keyword.

        You need to show the actual code you tried. Much, much better is to rework your code into a stand alone test script so we can run exactly what you are running with the same data. Something like:

        #!/usr/bin/perl use strict; use warnings; my $keyword = 'file'; # Search for the key pattern in the file information. while (defined (my $line = <DATA>)) { next if $line !~ /\b\Q$keyword\E\b/; print "Found key word $keyword on line $.\n"; exit; } print "Keyword not found\n"; __DATA__ Hi, I am a newbie to perl. I am trying to pass the filename and search + for a keyword in that file and if found print that line else print not found + message. However though my file has the keyword I get not found message.Please +help.I

        Prints:

        Found key word file on line 2
        True laziness is hard work
Re: Error using grep
by choroba (Cardinal) on Mar 28, 2011 at 23:54 UTC
    You chop the keyword, but you do not chop the lines. chomp might be better for both.
Re: Error using grep
by wind (Priest) on Mar 28, 2011 at 23:59 UTC
    Use a regex and add boundary conditions \b if you want them:
    if (grep {/\Q$key\E/} @lines) {