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

I have an input of log report like below.

7/21/2009 5:47:29 PM:> DATA
7/21/2009 5:48:49 PM:> DATA1
7/21/2009 5:49:20 PM:> FIND
7/21/2009 5:50:39 PM:> DATA3
7/21/2009 5:51:29 PM:> DATA4
7/21/2009 5:52:59 PM:> DATA5
7/21/2009 5:53:19 PM:> DATA6

I need to find the date and time of the text "FIND" and i need to check with internal system time. Whether this text FIND occurs within 30 minutes of system time then i need to print yes or no. I need some shortway to do this.

Replies are listed 'Best First'.
Re: Find the text
by chromatic (Archbishop) on Jul 28, 2009 at 08:03 UTC

    What code do you have so far? Where are you stuck?

Re: Find the text
by si_lence (Deacon) on Jul 28, 2009 at 08:02 UTC
    You need to convert the date to something that can be compared. Epoch might be a good choice.
    Dates are always a bit tricky to deal with (time zones, daylight saving, ...) but if you know your format you can use something like the following as a starting point

    use strict; use warnings; use Time::Local; while (<DATA>) { if (/FIND/) { my $now = time; my ($month, $day, $year, $hours, $minutes, $seconds, $AMPM) = +split /\/| |:/; $hours += 12 if $AMPM eq 'PM'; my $time = timegm($seconds, $minutes, $hours, $day, $month-1, +$year-1900); print "within 30 mins" if $now - $time < 30*60; } } __DATA__ 7/21/2009 5:47:29 PM:> DATA 7/21/2009 5:48:49 PM:> DATA1 7/21/2009 5:49:20 PM:> FIND 7/28/2009 9:49:20 AM:> FIND 7/21/2009 5:50:39 PM:> DATA3 7/21/2009 5:51:29 PM:> DATA4 7/21/2009 5:52:59 PM:> DATA5 7/21/2009 5:53:19 PM:> DATA6
    cheers, si_lence
Re: Find the text
by Marshall (Canon) on Jul 28, 2009 at 09:16 UTC
    I will get you started. This gets you the time string. Convert that to epoch. Convert current time to epoch. Then compare within 30min*60secs_per_minute = +- 1800 seconds.
    #!/usr/bin/perl -w use strict; while (<DATA>) { chomp; my ($time, $type) = split(/:>/,$_); if ($type =~ m/\s*FIND/) { print "I need to something with: $time\n"; } } #PRINTS: #I need to something with: 7/21/2009 5:49:20 PM #I need to something with: 7/21/2009 5:52:59 PM __DATA__ 7/21/2009 5:47:29 PM:> DATA 7/21/2009 5:48:49 PM:> DATA1 7/21/2009 5:49:20 PM:> FIND 7/21/2009 5:50:39 PM:> DATA3 7/21/2009 5:51:29 PM:> DATA4 7/21/2009 5:52:59 PM:> FIND 7/21/2009 5:53:19 PM:> DATA6
      I am trying using the below method.. Not yet completed... I just collected half an hour details with my system time and i need to find using this.
      my $time=0; while ($time <= 1800) { my ($sec,$min,$hour,$day,$month,$year) = localtime(time()-$time); $year = $year+1900; $month++; if ($hour >12) {$hour=$hour-12;} my $date=sprintf "%d/%d/%d %d:%02d:00", $month, $day, $year, $hour, $m +in; push(@array, $date); $time+=60; }

        It looks like you are trying to iterate over all whole minutes in a 30 minutes interval. That solution is very ineffective.

        If you have two dates, one from your file and one from the system time, just ensure that they are unix time (seconds since 1/1/1970 00:00) and then subtract one from the other and then see if the result is between 0 and 1800. This is the criteria that decides if a given FIND line is taking place within the next half hour.

        System time is already in unix time, so all you need is converting the time stamps from the file to seconds since epoch. There are plenty of modules that can do it for you.

        Also, please do this:

        • use warnings;
        • use strict;
        • Indent your code.
Re: Find the text
by imrags (Monk) on Jul 28, 2009 at 07:54 UTC
    What is the long way that you have come up with? ;)
    Anyway, you can use normal localtime and use split function to get it
    Raghu