@@ -317,26 +317,29 @@ impl Div<i32,Duration> for Duration {
317
317
318
318
impl fmt:: Show for Duration {
319
319
fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
320
- let days = self . num_days ( ) ;
321
- let secs = self . secs - days * SECS_PER_DAY ;
320
+ // technically speaking, negative duration is not valid ISO 8601,
321
+ // but we need to print it anyway.
322
+ let ( abs, sign) = if self . secs < 0 { ( -self , "-" ) } else { ( * self , "" ) } ;
323
+
324
+ let days = abs. secs / SECS_PER_DAY ;
325
+ let secs = abs. secs - days * SECS_PER_DAY ;
322
326
let hasdate = days != 0 ;
323
- let hastime = ( secs != 0 || self . nanos != 0 ) || !hasdate;
327
+ let hastime = ( secs != 0 || abs. nanos != 0 ) || !hasdate;
328
+
329
+ try!( write ! ( f, "{}P" , sign) ) ;
324
330
325
- try!( write ! ( f, "P" ) ) ;
326
331
if hasdate {
327
- // technically speaking the negative part is not the valid ISO 8601,
328
- // but we need to print it anyway.
329
332
try!( write ! ( f, "{}D" , days) ) ;
330
333
}
331
334
if hastime {
332
- if self . nanos == 0 {
335
+ if abs . nanos == 0 {
333
336
try!( write ! ( f, "T{}S" , secs) ) ;
334
- } else if self . nanos % NANOS_PER_MILLI == 0 {
335
- try!( write ! ( f, "T{}.{:03}S" , secs, self . nanos / NANOS_PER_MILLI ) ) ;
336
- } else if self . nanos % NANOS_PER_MICRO == 0 {
337
- try!( write ! ( f, "T{}.{:06}S" , secs, self . nanos / NANOS_PER_MICRO ) ) ;
337
+ } else if abs . nanos % NANOS_PER_MILLI == 0 {
338
+ try!( write ! ( f, "T{}.{:03}S" , secs, abs . nanos / NANOS_PER_MILLI ) ) ;
339
+ } else if abs . nanos % NANOS_PER_MICRO == 0 {
340
+ try!( write ! ( f, "T{}.{:06}S" , secs, abs . nanos / NANOS_PER_MICRO ) ) ;
338
341
} else {
339
- try!( write ! ( f, "T{}.{:09}S" , secs, self . nanos) ) ;
342
+ try!( write ! ( f, "T{}.{:09}S" , secs, abs . nanos) ) ;
340
343
}
341
344
}
342
345
Ok ( ( ) )
@@ -540,13 +543,15 @@ mod tests {
540
543
let d: Duration = Zero :: zero ( ) ;
541
544
assert_eq ! ( d. to_string( ) , "PT0S" . to_string( ) ) ;
542
545
assert_eq ! ( Duration :: days( 42 ) . to_string( ) , "P42D" . to_string( ) ) ;
543
- assert_eq ! ( Duration :: days( -42 ) . to_string( ) , "P-42D " . to_string( ) ) ;
546
+ assert_eq ! ( Duration :: days( -42 ) . to_string( ) , "-P42D " . to_string( ) ) ;
544
547
assert_eq ! ( Duration :: seconds( 42 ) . to_string( ) , "PT42S" . to_string( ) ) ;
545
548
assert_eq ! ( Duration :: milliseconds( 42 ) . to_string( ) , "PT0.042S" . to_string( ) ) ;
546
549
assert_eq ! ( Duration :: microseconds( 42 ) . to_string( ) , "PT0.000042S" . to_string( ) ) ;
547
550
assert_eq ! ( Duration :: nanoseconds( 42 ) . to_string( ) , "PT0.000000042S" . to_string( ) ) ;
548
551
assert_eq ! ( ( Duration :: days( 7 ) + Duration :: milliseconds( 6543 ) ) . to_string( ) ,
549
552
"P7DT6.543S" . to_string( ) ) ;
553
+ assert_eq ! ( Duration :: seconds( -86401 ) . to_string( ) , "-P1DT1S" . to_string( ) ) ;
554
+ assert_eq ! ( Duration :: nanoseconds( -1 ) . to_string( ) , "-PT0.000000001S" . to_string( ) ) ;
550
555
551
556
// the format specifier should have no effect on `Duration`
552
557
assert_eq ! ( format!( "{:30}" , Duration :: days( 1 ) + Duration :: milliseconds( 2345 ) ) ,
0 commit comments