in reply to Unexpected behaviour of /x Regexp modifier?

It appears to me that the basic file format would indicate that a split using white space (/\s+/) and then a sub-parsing using more splits and regex's would work out better rather doing the whole job with one regex from the start. Regex can do just about anything, but I recommend to separate the job into smaller pieces where possible.

It looks like you have some sort of an ID, then a date/time combo and then an error_code/description combo.

As a general hint for dealing with what looks to be a log file of some sort, convert the date/time into what is called "epoch time". This is a time expressed in seconds, +-seconds from approx. January 1, 1970. This simplifies "date/time" math because everything is now an integer number of seconds, i.e. the time 24 hours earlier than now is -(24*60*60) seconds. The code below shows how to do that.

The Perl array of pointers to hash is close to a traditional C 2-D array and the code below shows how to do that too (Perl data structures don't have a one<->one mapping with C). Have fun, hope this helps.

#!/usr/bin/perl -w use strict; use Time::Local; my @ListOfRecords = (); #a list of hash while (<DATA>) { next if /^\s*$/; #skip blank lines my %record=(); my ($meter,$date,$time,$text) = split; my $epoch =dateTime2Epoch($date,$time); my ($code,$description)= $_ =~ /(\d+)_(\w+)/; #demo of a "hash slice... @record {"Meter","Epoch","Code","Descript"}= ($meter, $epoch, $code, $description); push (@ListOfRecords, \%record); } #### # just an example dump # could be sorted before this # could be written in fewer lines # this is just an example #### raw_dump(\@ListOfRecords); sub raw_dump { my $Loh=shift; foreach my $href (@$Loh) { foreach my $record (keys (%$href)) { if ($record eq "Epoch") { print "Date Time = ".epoch2datetime($href->{$record}) ."\n"; } else { print "$record=$href->{$record}\n"; } } print "\n"; } } #$epoch=dateTime2Epoch("09-11-2007", "15:27:30"); sub dateTime2Epoch { my ($date,$time) = @_; my($day,$month,$year)= split(/-/,$date); my($hour,$min,$sec)=split (/:/,$time); my $epoch_time = timegm($sec,$min,$hour,$day,$month-1, $year-1900); return $epoch_time; } sub epoch2datetime { my $epoch = shift; my($seconds, $minutes, $hours, $days, $month, $year) = gmtime($epoch); my $str_date_time =sprintf("%02d-%02d-%04d %02d:%02d:%02d", $days,$month+1,$year+1900, $hours, $minutes, $seconds); return ($str_date_time); } # prints: # Code=102 # Descript=Low_Alarm # Meter=000.000.002.249-2-P # Date Time = 09-11-2007 15:27:30 # # Code=102 # Descript=Low_Alarm # Meter=000.000.002.249-2-P # Date Time = 09-11-2007 16:44:18 # # Code=202 # Descript=Low_Repeat # Meter=000.000.002.249-2-P # Date Time = 09-11-2007 16:44:18 __DATA__ 000.000.002.249-2-P 09-11-2007 15:27:30 102_Low_Alarm 000.000.002.249-2-P 09-11-2007 16:44:18 102_Low_Alarm 000.000.002.249-2-P 09-11-2007 16:44:18 202_Low_Repeat