Don’t treat your date like just another number

There’s more than one type of date that can prove awkward, but this is Perl, and so I’m talking calendar dates. And when I say awkward, I mean the interpretation of how a date should be treated.

It’s very tempting when we see something like this, to think we can always get away with comparing dates as we see them.


Surely, it’s a simple case of comparing by means of greater than / less than? That is to say, if we can do this…

use strict;
use warnings;

# if 4 is greater than 2 - which it is
if ( 4 > 2 ) {
  print "Four is greater than two" , "\n";
    else {
      print "Four is not greater than two";

Which, as you might expect, outputs…

Four is greater than two

… we can do something similar with a date?

# if 1995 comes before 1996 - which it does
if ( 01/01/1996 > 10/01/1995) {
  print "1996 is a later date than 1995 " , "\n";
    else {
      print "Soemthing not quite right" , "\n";

Which produces…

Something not quite right

The short answer is, we can’t treat these as dates… yet. We’re just treating them as strings or numbers, depending how you use the operator that is doing the comparing. And if we are treating them as numbers, we’re doing unwanted procedures with the / character, that is creating divisional calculations.

So, here’s something more robust.

use strict;
use warnings;
use DateTime::Format::Strptime;
use feature 'say';

# create a date format - British style

my $format = DateTime::Format::Strptime->new( pattern => '%d/%m/%Y' );

# create a date to use to compare against what's in __DATA__

my $compare_date = DateTime->new(year   => 1994, 
                                 month  => 12, 
                                 day    => 31, 
                                 formatter => $format
while (<DATA>) {
	my ($id,$name,$date_text) = split (/,/,$_);
	# set the text in data to Date objects
    my $date = $format->parse_datetime($date_text);
    # set the formatting style
    $format = $date->formatter();
    # if 31/12/1994 is a later date than the string-to-date object
    if ( $compare_date > $date) {
		say "$id date $date comes before " . $compare_date;
	# if 31/12/1994 is an earlier date than the string-to-date object
	  else {
		say "$id date $date comes after " . $compare_date;

close DATA;


We create a formatting style for dates – date of month, month and year using DateTime::Format::Strptime and assign it to $format.

We set a date object $compare_date with DateTime. This is used to compare the dates parsed in __DATA__.

If we don’t set the format for $date (taken from $date_text in __DATA__) on lines 28 and 29, then $date will be output using ISO 8601 format.

The output is…

ID1 date 10/12/1994 comes before 31/12/1994
ID2 date 11/12/1994 comes before 31/12/1994
ID3 date 01/01/1995 comes after 31/12/1994
ID4 date 02/01/1995 comes after 31/12/1994
ID5 date 01/01/1996 comes after 31/12/1994

Until the next time.

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

%d bloggers like this: