7
use DateTime ;

my $date = "2010-08-02 09:10:08";

my $dt = DateTime->now( time_zone => 'local' )->set_time_zone('floating');
print $dt->subtract_datetime($date);

It's not working; what is the problem?

The error message is:

Can't call method "time_zone" without a package or object reference at
/opt/perl/perl5.12/lib/site_perl/5.12.0/x86_64-linux/DateTime.pm line 1338
1
  • define your $data var as a datetime : my $date = DateTime->new(year=>2010, month=>8, day=>2, hour=>9, minute=>10, second=>8); Commented Aug 2, 2010 at 15:24

3 Answers 3

18

You need to convert date strings into DateTime objects first, using a customized format or one of the many DateTime::Format::* libraries available. You're using a format commonly used in databases, so I've selected the MySQL formatter (and then defined a custom duration formatter for the end result, copied from the examples in DateTime::Format::Duration):

use DateTime;
use DateTime::Format::MySQL;
use DateTime::Format::Duration;

my $date = "2010-08-02 09:10:08";

my $dt1 = DateTime->now(time_zone => 'floating', formatter => 'DateTime::Format::MySQL');
my $dt2 = DateTime::Format::MySQL->parse_datetime($date);

my $duration = $dt1 - $dt2;
my $format = DateTime::Format::Duration->new(
    pattern => '%Y years, %m months, %e days, %H hours, %M minutes, %S seconds'
);
print $format->format_duration($duration);

# prints:
# 0 years, 00 months, 0 days, 00 hours, 421 minutes, 03 seconds
Sign up to request clarification or add additional context in comments.

2 Comments

Not sure if anyone will see this, but why does the output come out as 00 hours and 421 minutes. why not 07 hours 01 minutes?
@JamesFinnegan because normalize => 1 wasn't included as an option to DateTime::Format::Duration->new(..). See metacpan.org/pod/DateTime::Format::Duration. When that option is added, the output shifts from 0 years, 113 months, 5 days, 00 hours, 804 minutes, 38 seconds to 9 years, 05 months, 5 days, 13 hours, 24 minutes, 38 seconds. (I should also note that at the time of my response above, I wasn't yet a maintainer of this module, but now I am.) ;)
6

$date must be a DateTime object, not a simple string. See DateTime. And, you can not simply print the return value of subtract_datetime because it returns a reference. You must use methods, such as hours, to extract useful info.

use strict;
use warnings;
use DateTime;

my $dt2 = DateTime->new(
                       year   => 2010,
                       month  => 8,
                       day    => 2,
                       hour   => 9,
                       minute => 10,
                       second => 8,
                       time_zone => 'local',
                     );

my $dt1 = DateTime->now( time_zone => 'local' )->set_time_zone('floating');

my $dur = $dt1->subtract_datetime($dt2);
print 'hours = ', $dur->hours(), "\n";

__END__

hours = 2

Comments

4

Well, at first sight, i guess that $dt->subtract_datetime(...) will work if you subtract two datetime objects.

ie : your $date should be a datetime

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.