in reply to Can't get hash keys to print

Hello Daren, and welcome to the Monastery!

Glad to see that hippo’s answer was what you were looking for. In the future, you should give an example of the input file, together with the output you expect from that example, and the output you actually get.

But I want to point out that your strategy of performing a regular expression match on Return code is and then splitting on : is potentially fragile: if there is whitespace between the colon and the return code digit, this whitespace will be included in the hash key. So you could, for example, end up with separate hash entries for “7” and “ 7”. A more robust solution would be to capture the return code in the regex match:

++$errors{$1} if $row =~ / \Q$string\E \s* : \s* (\d+) $ /x;

Hope that helps,

Athanasius <°(((><contra mundum Iustus alius egestas vitae, eros Piratica,

Replies are listed 'Best First'.
Re^2: Can't get hash keys to print
by Daren (Initiate) on Aug 24, 2015 at 15:08 UTC
    Athanasius,
    You are spot on, esp after the trailing carriage bit me in the butt on the keys.
    I need to get better on thinking what could break my scripts.
    Thanks for your help!
Re^2: Can't get hash keys to print
by Daren (Initiate) on Aug 24, 2015 at 18:41 UTC
    Hello again, I understand your suggested expression, and I feel like it should work but it isn't. It isn't matching anything.
    This is a few sample input lines...
    2015/04/06 12:38:15 (9):(5564) Return code is :55
    2015/04/06 12:38:15 (9):(6600) Return code is :55
    2015/04/06 12:41:31 (9):(3604) Return code is :1

      Assuming there are any number of  space \t \r \n etc. at the end of each line, try something like:

      c:\@Work\Perl\monks>perl -wMstrict -MData::Dump -le "my $string = 'Return code is'; ;; my %errors; for my $row ( qq{2015/04/06 12:38:15 (9):(5564) Return code is :55\n\r\n}, qq{2015/04/06 12:38:15 (9):(6600) Return code is :55 \r\n\r}, qq{2015/04/06 12:41:31 (9):(3604) Return code is :1\t\n\r}, ) { ++$errors{$1} if $row =~ m{ \Q$string\E \s* : (\d+) \s* \z }xms; } dd \%errors; ;; my $total; for my $err_no (sort { $a <=> $b } keys %errors) { print qq{error $err_no - $errors{$err_no} total}; $total += $errors{$err_no}; } print qq{total errors: $total}; " { 1 => 1, 55 => 2 } error 1 - 1 total error 55 - 2 total total errors: 3


      Give a man a fish:  <%-{-{-{-<

      Something else isn't right then. Using the data you supplied above (which you should copy to your actual question for future readers), and copy/pasting Athanasius' regex, here's what I get in %errors:

      use warnings; use strict; my $string = "Return code is"; my %errors; while (<DATA>){ ++$errors{$1} if /\Q$string\E \s* : \s* (\d+) $ /x; } while (my ($k, $v) = each %errors){ print "$k: $v\n"; } __DATA__ 2015/04/06 12:38:15 (9):(5564) Return code is :55 2015/04/06 12:38:15 (9):(6600) Return code is :55 2015/04/06 12:41:31 (9):(3604) Return code is :1

      Output:

      1: 1 55: 2
        I think it's the format of the input file. (UNIX)
        I removed the $ from the regex and it works fine.
        I don't quite understand why though.