时间戳到午夜左右的毫秒转换搞砸了

时间:2014-02-25 22:30:47

标签: perl

我正在使用以下函数将格式(例如)02:49:02.506中的时间戳转换为perl中的毫秒。

sub to_millis {
    my( $hours, $minutes, $seconds, $millis) = split /:/, $_[0];

    $millis += 1000 * $seconds;
    $millis += 1000 * 60 * $minutes;
    $millis += 1000 * 60 * 60 * $hours;

    return $millis;
}

然后我使用从上面的例程生成的毫秒来计算两个时间戳之间的时间差(以毫秒为单位)。这整天工作正常,但是在时间戳变为00:00:00000的午夜时分弄乱了。因此,生成1小时(从早上12点到凌晨1点)的任何日志都会得到时间戳差异的负值。由于我的时间戳没有日期,我该如何解决这个问题?我试图在移动设备上执行此操作,该设备没有安装许多perl模块。所以我没有自由使用所有可用的perl模块。

4 个答案:

答案 0 :(得分:1)

如果您知道两个时间戳的顺序,并且如果您知道它们相隔不超过24小时,那么如果您得到负差异则会增加24小时(86,400,000毫秒)。

如果您没有这些信息,那么您将无法区分2分钟的跨度和24小时2分钟的跨度。

答案 1 :(得分:0)

你有两个时间戳,A和B.如果B在概念上总是“在”A之后,但从A到B的间隔可能越过日期边界,那么

if (B < A) B+=86400000

然后进行减法。或者等效地

diff = B - A
if (diff < 0) diff+=86400000

但是,如果不保证B总是“在”A之后,则必须确定差异的正负值的可接受范围。如果超过半天您运气不好,就无法解决问题,因为您无法判断负间隔是否代表真正的负间隔,或者是否恰好跨越了一天的边界。

答案 2 :(得分:0)

要在午夜处理环绕:

$elapsed_ms = $t2_ms - $t1_ms;
if ($elapsed_ms < 0) $elapsed_ms += (24 * 60 * 60 * 1000);

答案 3 :(得分:0)

我认为你的时间戳永远不会超过23小时59分钟?

我们需要两个时间戳AB。我假设A发生在B之前。

通常,如果A小于B,我知道我可以从A中减去B来节省时间。但是,在这种情况下,A大于B。我现在不得不假设我已经在午夜时分缠身。我该怎么办?

我知道AB之间的差异是A到午夜, PLUS B。

例如,A为11:58:30,B为00:02:00

我知道A将在午夜前90秒,而B将再增加120秒。因此,总差异将是90 + 120 = 210秒。

使用你的日常工作:

my $midnight = to_millis( "23:59:00:000" );  # Need the time at midnight
my $a_time   = to_millis( $a_timestamp   );
my $b_time   = to_millis( $b_timestamp   );
my $time_diff;

if ( $a_time < $b_time ) {  # Normal timestamp issue
   $time_diff = $b_time - $a_time;
}
else {                      # We wrapped around midnight!
    my $first_part = $midnight - $a_time;   # Time from A to midnight
    $time_diff = $first_part + $b_time      # We add the time from midnite to B
}