1 // This is a part of Chrono.
2 // See README.md and LICENSE.txt for details.
3 
4 //! ISO 8601 time without timezone.
5 
6 #[cfg(feature = "alloc")]
7 use core::borrow::Borrow;
8 use core::ops::{Add, AddAssign, Sub, SubAssign};
9 use core::time::Duration;
10 use core::{fmt, str};
11 
12 #[cfg(any(feature = "rkyv", feature = "rkyv-16", feature = "rkyv-32", feature = "rkyv-64"))]
13 use rkyv::{Archive, Deserialize, Serialize};
14 
15 #[cfg(feature = "alloc")]
16 use crate::format::DelayedFormat;
17 use crate::format::{
18     parse, parse_and_remainder, write_hundreds, Fixed, Item, Numeric, Pad, ParseError, ParseResult,
19     Parsed, StrftimeItems,
20 };
21 use crate::{expect, try_opt};
22 use crate::{FixedOffset, TimeDelta, Timelike};
23 
24 #[cfg(feature = "rustc-serialize")]
25 mod rustc_serialize;
26 
27 #[cfg(feature = "serde")]
28 mod serde;
29 
30 #[cfg(test)]
31 mod tests;
32 
33 /// ISO 8601 time without timezone.
34 /// Allows for the nanosecond precision and optional leap second representation.
35 ///
36 /// # Leap Second Handling
37 ///
38 /// Since 1960s, the manmade atomic clock has been so accurate that
39 /// it is much more accurate than Earth's own motion.
40 /// It became desirable to define the civil time in terms of the atomic clock,
41 /// but that risks the desynchronization of the civil time from Earth.
42 /// To account for this, the designers of the Coordinated Universal Time (UTC)
43 /// made that the UTC should be kept within 0.9 seconds of the observed Earth-bound time.
44 /// When the mean solar day is longer than the ideal (86,400 seconds),
45 /// the error slowly accumulates and it is necessary to add a **leap second**
46 /// to slow the UTC down a bit.
47 /// (We may also remove a second to speed the UTC up a bit, but it never happened.)
48 /// The leap second, if any, follows 23:59:59 of June 30 or December 31 in the UTC.
49 ///
50 /// Fast forward to the 21st century,
51 /// we have seen 26 leap seconds from January 1972 to December 2015.
52 /// Yes, 26 seconds. Probably you can read this paragraph within 26 seconds.
53 /// But those 26 seconds, and possibly more in the future, are never predictable,
54 /// and whether to add a leap second or not is known only before 6 months.
55 /// Internet-based clocks (via NTP) do account for known leap seconds,
56 /// but the system API normally doesn't (and often can't, with no network connection)
57 /// and there is no reliable way to retrieve leap second information.
58 ///
59 /// Chrono does not try to accurately implement leap seconds; it is impossible.
60 /// Rather, **it allows for leap seconds but behaves as if there are *no other* leap seconds.**
61 /// Various operations will ignore any possible leap second(s)
62 /// except when any of the operands were actually leap seconds.
63 ///
64 /// If you cannot tolerate this behavior,
65 /// you must use a separate `TimeZone` for the International Atomic Time (TAI).
66 /// TAI is like UTC but has no leap seconds, and thus slightly differs from UTC.
67 /// Chrono does not yet provide such implementation, but it is planned.
68 ///
69 /// ## Representing Leap Seconds
70 ///
71 /// The leap second is indicated via fractional seconds more than 1 second.
72 /// This makes possible to treat a leap second as the prior non-leap second
73 /// if you don't care about sub-second accuracy.
74 /// You should use the proper formatting to get the raw leap second.
75 ///
76 /// All methods accepting fractional seconds will accept such values.
77 ///
78 /// ```
79 /// use chrono::{NaiveDate, NaiveTime, Utc};
80 ///
81 /// let t = NaiveTime::from_hms_milli_opt(8, 59, 59, 1_000).unwrap();
82 ///
83 /// let dt1 = NaiveDate::from_ymd_opt(2015, 7, 1).unwrap().and_hms_micro_opt(8, 59, 59, 1_000_000).unwrap();
84 ///
85 /// let dt2 = NaiveDate::from_ymd_opt(2015, 6, 30).unwrap().and_hms_nano_opt(23, 59, 59, 1_000_000_000).unwrap().and_local_timezone(Utc).unwrap();
86 /// # let _ = (t, dt1, dt2);
87 /// ```
88 ///
89 /// Note that the leap second can happen anytime given an appropriate time zone;
90 /// 2015-07-01 01:23:60 would be a proper leap second if UTC+01:24 had existed.
91 /// Practically speaking, though, by the time of the first leap second on 1972-06-30,
92 /// every time zone offset around the world has standardized to the 5-minute alignment.
93 ///
94 /// ## Date And Time Arithmetics
95 ///
96 /// As a concrete example, let's assume that `03:00:60` and `04:00:60` are leap seconds.
97 /// In reality, of course, leap seconds are separated by at least 6 months.
98 /// We will also use some intuitive concise notations for the explanation.
99 ///
100 /// `Time + TimeDelta`
101 /// (short for [`NaiveTime::overflowing_add_signed`](#method.overflowing_add_signed)):
102 ///
103 /// - `03:00:00 + 1s = 03:00:01`.
104 /// - `03:00:59 + 60s = 03:01:59`.
105 /// - `03:00:59 + 61s = 03:02:00`.
106 /// - `03:00:59 + 1s = 03:01:00`.
107 /// - `03:00:60 + 1s = 03:01:00`.
108 ///   Note that the sum is identical to the previous.
109 /// - `03:00:60 + 60s = 03:01:59`.
110 /// - `03:00:60 + 61s = 03:02:00`.
111 /// - `03:00:60.1 + 0.8s = 03:00:60.9`.
112 ///
113 /// `Time - TimeDelta`
114 /// (short for [`NaiveTime::overflowing_sub_signed`](#method.overflowing_sub_signed)):
115 ///
116 /// - `03:00:00 - 1s = 02:59:59`.
117 /// - `03:01:00 - 1s = 03:00:59`.
118 /// - `03:01:00 - 60s = 03:00:00`.
119 /// - `03:00:60 - 60s = 03:00:00`.
120 ///   Note that the result is identical to the previous.
121 /// - `03:00:60.7 - 0.4s = 03:00:60.3`.
122 /// - `03:00:60.7 - 0.9s = 03:00:59.8`.
123 ///
124 /// `Time - Time`
125 /// (short for [`NaiveTime::signed_duration_since`](#method.signed_duration_since)):
126 ///
127 /// - `04:00:00 - 03:00:00 = 3600s`.
128 /// - `03:01:00 - 03:00:00 = 60s`.
129 /// - `03:00:60 - 03:00:00 = 60s`.
130 ///   Note that the difference is identical to the previous.
131 /// - `03:00:60.6 - 03:00:59.4 = 1.2s`.
132 /// - `03:01:00 - 03:00:59.8 = 0.2s`.
133 /// - `03:01:00 - 03:00:60.5 = 0.5s`.
134 ///   Note that the difference is larger than the previous,
135 ///   even though the leap second clearly follows the previous whole second.
136 /// - `04:00:60.9 - 03:00:60.1 =
137 ///   (04:00:60.9 - 04:00:00) + (04:00:00 - 03:01:00) + (03:01:00 - 03:00:60.1) =
138 ///   60.9s + 3540s + 0.9s = 3601.8s`.
139 ///
140 /// In general,
141 ///
142 /// - `Time + TimeDelta` unconditionally equals to `TimeDelta + Time`.
143 ///
144 /// - `Time - TimeDelta` unconditionally equals to `Time + (-TimeDelta)`.
145 ///
146 /// - `Time1 - Time2` unconditionally equals to `-(Time2 - Time1)`.
147 ///
148 /// - Associativity does not generally hold, because
149 ///   `(Time + TimeDelta1) - TimeDelta2` no longer equals to `Time + (TimeDelta1 - TimeDelta2)`
150 ///   for two positive durations.
151 ///
152 ///     - As a special case, `(Time + TimeDelta) - TimeDelta` also does not equal to `Time`.
153 ///
154 ///     - If you can assume that all durations have the same sign, however,
155 ///       then the associativity holds:
156 ///       `(Time + TimeDelta1) + TimeDelta2` equals to `Time + (TimeDelta1 + TimeDelta2)`
157 ///       for two positive durations.
158 ///
159 /// ## Reading And Writing Leap Seconds
160 ///
161 /// The "typical" leap seconds on the minute boundary are
162 /// correctly handled both in the formatting and parsing.
163 /// The leap second in the human-readable representation
164 /// will be represented as the second part being 60, as required by ISO 8601.
165 ///
166 /// ```
167 /// use chrono::{Utc, NaiveDate};
168 ///
169 /// let dt = NaiveDate::from_ymd_opt(2015, 6, 30).unwrap().and_hms_milli_opt(23, 59, 59, 1_000).unwrap().and_local_timezone(Utc).unwrap();
170 /// assert_eq!(format!("{:?}", dt), "2015-06-30T23:59:60Z");
171 /// ```
172 ///
173 /// There are hypothetical leap seconds not on the minute boundary nevertheless supported by Chrono.
174 /// They are allowed for the sake of completeness and consistency; there were several "exotic" time
175 /// zone offsets with fractional minutes prior to UTC after all.
176 /// For such cases the human-readable representation is ambiguous and would be read back to the next
177 /// non-leap second.
178 ///
179 /// A `NaiveTime` with a leap second that is not on a minute boundary can only be created from a
180 /// [`DateTime`](crate::DateTime) with fractional minutes as offset, or using
181 /// [`Timelike::with_nanosecond()`].
182 ///
183 /// ```
184 /// use chrono::{FixedOffset, NaiveDate, TimeZone};
185 ///
186 /// let paramaribo_pre1945 = FixedOffset::east_opt(-13236).unwrap(); // -03:40:36
187 /// let leap_sec_2015 =
188 ///     NaiveDate::from_ymd_opt(2015, 6, 30).unwrap().and_hms_milli_opt(23, 59, 59, 1_000).unwrap();
189 /// let dt1 = paramaribo_pre1945.from_utc_datetime(&leap_sec_2015);
190 /// assert_eq!(format!("{:?}", dt1), "2015-06-30T20:19:24-03:40:36");
191 /// assert_eq!(format!("{:?}", dt1.time()), "20:19:24");
192 ///
193 /// let next_sec = NaiveDate::from_ymd_opt(2015, 7, 1).unwrap().and_hms_opt(0, 0, 0).unwrap();
194 /// let dt2 = paramaribo_pre1945.from_utc_datetime(&next_sec);
195 /// assert_eq!(format!("{:?}", dt2), "2015-06-30T20:19:24-03:40:36");
196 /// assert_eq!(format!("{:?}", dt2.time()), "20:19:24");
197 ///
198 /// assert!(dt1.time() != dt2.time());
199 /// assert!(dt1.time().to_string() == dt2.time().to_string());
200 /// ```
201 ///
202 /// Since Chrono alone cannot determine any existence of leap seconds,
203 /// **there is absolutely no guarantee that the leap second read has actually happened**.
204 #[derive(PartialEq, Eq, Hash, PartialOrd, Ord, Copy, Clone)]
205 #[cfg_attr(
206     any(feature = "rkyv", feature = "rkyv-16", feature = "rkyv-32", feature = "rkyv-64"),
207     derive(Archive, Deserialize, Serialize),
208     archive(compare(PartialEq, PartialOrd)),
209     archive_attr(derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Debug, Hash))
210 )]
211 #[cfg_attr(feature = "rkyv-validation", archive(check_bytes))]
212 pub struct NaiveTime {
213     secs: u32,
214     frac: u32,
215 }
216 
217 #[cfg(feature = "arbitrary")]
218 impl arbitrary::Arbitrary<'_> for NaiveTime {
arbitrary(u: &mut arbitrary::Unstructured) -> arbitrary::Result<NaiveTime>219     fn arbitrary(u: &mut arbitrary::Unstructured) -> arbitrary::Result<NaiveTime> {
220         let mins = u.int_in_range(0..=1439)?;
221         let mut secs = u.int_in_range(0..=60)?;
222         let mut nano = u.int_in_range(0..=999_999_999)?;
223         if secs == 60 {
224             secs = 59;
225             nano += 1_000_000_000;
226         }
227         let time = NaiveTime::from_num_seconds_from_midnight_opt(mins * 60 + secs, nano)
228             .expect("Could not generate a valid chrono::NaiveTime. It looks like implementation of Arbitrary for NaiveTime is erroneous.");
229         Ok(time)
230     }
231 }
232 
233 impl NaiveTime {
234     /// Makes a new `NaiveTime` from hour, minute and second.
235     ///
236     /// No [leap second](#leap-second-handling) is allowed here;
237     /// use `NaiveTime::from_hms_*` methods with a subsecond parameter instead.
238     ///
239     /// # Panics
240     ///
241     /// Panics on invalid hour, minute and/or second.
242     #[deprecated(since = "0.4.23", note = "use `from_hms_opt()` instead")]
243     #[inline]
244     #[must_use]
from_hms(hour: u32, min: u32, sec: u32) -> NaiveTime245     pub const fn from_hms(hour: u32, min: u32, sec: u32) -> NaiveTime {
246         expect!(NaiveTime::from_hms_opt(hour, min, sec), "invalid time")
247     }
248 
249     /// Makes a new `NaiveTime` from hour, minute and second.
250     ///
251     /// The millisecond part is allowed to exceed 1,000,000,000 in order to represent a
252     /// [leap second](#leap-second-handling), but only when `sec == 59`.
253     ///
254     /// # Errors
255     ///
256     /// Returns `None` on invalid hour, minute and/or second.
257     ///
258     /// # Example
259     ///
260     /// ```
261     /// use chrono::NaiveTime;
262     ///
263     /// let from_hms_opt = NaiveTime::from_hms_opt;
264     ///
265     /// assert!(from_hms_opt(0, 0, 0).is_some());
266     /// assert!(from_hms_opt(23, 59, 59).is_some());
267     /// assert!(from_hms_opt(24, 0, 0).is_none());
268     /// assert!(from_hms_opt(23, 60, 0).is_none());
269     /// assert!(from_hms_opt(23, 59, 60).is_none());
270     /// ```
271     #[inline]
272     #[must_use]
from_hms_opt(hour: u32, min: u32, sec: u32) -> Option<NaiveTime>273     pub const fn from_hms_opt(hour: u32, min: u32, sec: u32) -> Option<NaiveTime> {
274         NaiveTime::from_hms_nano_opt(hour, min, sec, 0)
275     }
276 
277     /// Makes a new `NaiveTime` from hour, minute, second and millisecond.
278     ///
279     /// The millisecond part can exceed 1,000
280     /// in order to represent the [leap second](#leap-second-handling).
281     ///
282     /// # Panics
283     ///
284     /// Panics on invalid hour, minute, second and/or millisecond.
285     #[deprecated(since = "0.4.23", note = "use `from_hms_milli_opt()` instead")]
286     #[inline]
287     #[must_use]
from_hms_milli(hour: u32, min: u32, sec: u32, milli: u32) -> NaiveTime288     pub const fn from_hms_milli(hour: u32, min: u32, sec: u32, milli: u32) -> NaiveTime {
289         expect!(NaiveTime::from_hms_milli_opt(hour, min, sec, milli), "invalid time")
290     }
291 
292     /// Makes a new `NaiveTime` from hour, minute, second and millisecond.
293     ///
294     /// The millisecond part is allowed to exceed 1,000,000,000 in order to represent a
295     /// [leap second](#leap-second-handling), but only when `sec == 59`.
296     ///
297     /// # Errors
298     ///
299     /// Returns `None` on invalid hour, minute, second and/or millisecond.
300     ///
301     /// # Example
302     ///
303     /// ```
304     /// use chrono::NaiveTime;
305     ///
306     /// let from_hmsm_opt = NaiveTime::from_hms_milli_opt;
307     ///
308     /// assert!(from_hmsm_opt(0, 0, 0, 0).is_some());
309     /// assert!(from_hmsm_opt(23, 59, 59, 999).is_some());
310     /// assert!(from_hmsm_opt(23, 59, 59, 1_999).is_some()); // a leap second after 23:59:59
311     /// assert!(from_hmsm_opt(24, 0, 0, 0).is_none());
312     /// assert!(from_hmsm_opt(23, 60, 0, 0).is_none());
313     /// assert!(from_hmsm_opt(23, 59, 60, 0).is_none());
314     /// assert!(from_hmsm_opt(23, 59, 59, 2_000).is_none());
315     /// ```
316     #[inline]
317     #[must_use]
from_hms_milli_opt( hour: u32, min: u32, sec: u32, milli: u32, ) -> Option<NaiveTime>318     pub const fn from_hms_milli_opt(
319         hour: u32,
320         min: u32,
321         sec: u32,
322         milli: u32,
323     ) -> Option<NaiveTime> {
324         let nano = try_opt!(milli.checked_mul(1_000_000));
325         NaiveTime::from_hms_nano_opt(hour, min, sec, nano)
326     }
327 
328     /// Makes a new `NaiveTime` from hour, minute, second and microsecond.
329     ///
330     /// The microsecond part is allowed to exceed 1,000,000,000 in order to represent a
331     /// [leap second](#leap-second-handling), but only when `sec == 59`.
332     ///
333     /// # Panics
334     ///
335     /// Panics on invalid hour, minute, second and/or microsecond.
336     #[deprecated(since = "0.4.23", note = "use `from_hms_micro_opt()` instead")]
337     #[inline]
338     #[must_use]
from_hms_micro(hour: u32, min: u32, sec: u32, micro: u32) -> NaiveTime339     pub const fn from_hms_micro(hour: u32, min: u32, sec: u32, micro: u32) -> NaiveTime {
340         expect!(NaiveTime::from_hms_micro_opt(hour, min, sec, micro), "invalid time")
341     }
342 
343     /// Makes a new `NaiveTime` from hour, minute, second and microsecond.
344     ///
345     /// The microsecond part is allowed to exceed 1,000,000,000 in order to represent a
346     /// [leap second](#leap-second-handling), but only when `sec == 59`.
347     ///
348     /// # Errors
349     ///
350     /// Returns `None` on invalid hour, minute, second and/or microsecond.
351     ///
352     /// # Example
353     ///
354     /// ```
355     /// use chrono::NaiveTime;
356     ///
357     /// let from_hmsu_opt = NaiveTime::from_hms_micro_opt;
358     ///
359     /// assert!(from_hmsu_opt(0, 0, 0, 0).is_some());
360     /// assert!(from_hmsu_opt(23, 59, 59, 999_999).is_some());
361     /// assert!(from_hmsu_opt(23, 59, 59, 1_999_999).is_some()); // a leap second after 23:59:59
362     /// assert!(from_hmsu_opt(24, 0, 0, 0).is_none());
363     /// assert!(from_hmsu_opt(23, 60, 0, 0).is_none());
364     /// assert!(from_hmsu_opt(23, 59, 60, 0).is_none());
365     /// assert!(from_hmsu_opt(23, 59, 59, 2_000_000).is_none());
366     /// ```
367     #[inline]
368     #[must_use]
from_hms_micro_opt( hour: u32, min: u32, sec: u32, micro: u32, ) -> Option<NaiveTime>369     pub const fn from_hms_micro_opt(
370         hour: u32,
371         min: u32,
372         sec: u32,
373         micro: u32,
374     ) -> Option<NaiveTime> {
375         let nano = try_opt!(micro.checked_mul(1_000));
376         NaiveTime::from_hms_nano_opt(hour, min, sec, nano)
377     }
378 
379     /// Makes a new `NaiveTime` from hour, minute, second and nanosecond.
380     ///
381     /// The nanosecond part is allowed to exceed 1,000,000,000 in order to represent a
382     /// [leap second](#leap-second-handling), but only when `sec == 59`.
383     ///
384     /// # Panics
385     ///
386     /// Panics on invalid hour, minute, second and/or nanosecond.
387     #[deprecated(since = "0.4.23", note = "use `from_hms_nano_opt()` instead")]
388     #[inline]
389     #[must_use]
from_hms_nano(hour: u32, min: u32, sec: u32, nano: u32) -> NaiveTime390     pub const fn from_hms_nano(hour: u32, min: u32, sec: u32, nano: u32) -> NaiveTime {
391         expect!(NaiveTime::from_hms_nano_opt(hour, min, sec, nano), "invalid time")
392     }
393 
394     /// Makes a new `NaiveTime` from hour, minute, second and nanosecond.
395     ///
396     /// The nanosecond part is allowed to exceed 1,000,000,000 in order to represent a
397     /// [leap second](#leap-second-handling), but only when `sec == 59`.
398     ///
399     /// # Errors
400     ///
401     /// Returns `None` on invalid hour, minute, second and/or nanosecond.
402     ///
403     /// # Example
404     ///
405     /// ```
406     /// use chrono::NaiveTime;
407     ///
408     /// let from_hmsn_opt = NaiveTime::from_hms_nano_opt;
409     ///
410     /// assert!(from_hmsn_opt(0, 0, 0, 0).is_some());
411     /// assert!(from_hmsn_opt(23, 59, 59, 999_999_999).is_some());
412     /// assert!(from_hmsn_opt(23, 59, 59, 1_999_999_999).is_some()); // a leap second after 23:59:59
413     /// assert!(from_hmsn_opt(24, 0, 0, 0).is_none());
414     /// assert!(from_hmsn_opt(23, 60, 0, 0).is_none());
415     /// assert!(from_hmsn_opt(23, 59, 60, 0).is_none());
416     /// assert!(from_hmsn_opt(23, 59, 59, 2_000_000_000).is_none());
417     /// ```
418     #[inline]
419     #[must_use]
from_hms_nano_opt(hour: u32, min: u32, sec: u32, nano: u32) -> Option<NaiveTime>420     pub const fn from_hms_nano_opt(hour: u32, min: u32, sec: u32, nano: u32) -> Option<NaiveTime> {
421         if (hour >= 24 || min >= 60 || sec >= 60)
422             || (nano >= 1_000_000_000 && sec != 59)
423             || nano >= 2_000_000_000
424         {
425             return None;
426         }
427         let secs = hour * 3600 + min * 60 + sec;
428         Some(NaiveTime { secs, frac: nano })
429     }
430 
431     /// Makes a new `NaiveTime` from the number of seconds since midnight and nanosecond.
432     ///
433     /// The nanosecond part is allowed to exceed 1,000,000,000 in order to represent a
434     /// [leap second](#leap-second-handling), but only when `secs % 60 == 59`.
435     ///
436     /// # Panics
437     ///
438     /// Panics on invalid number of seconds and/or nanosecond.
439     #[deprecated(since = "0.4.23", note = "use `from_num_seconds_from_midnight_opt()` instead")]
440     #[inline]
441     #[must_use]
from_num_seconds_from_midnight(secs: u32, nano: u32) -> NaiveTime442     pub const fn from_num_seconds_from_midnight(secs: u32, nano: u32) -> NaiveTime {
443         expect!(NaiveTime::from_num_seconds_from_midnight_opt(secs, nano), "invalid time")
444     }
445 
446     /// Makes a new `NaiveTime` from the number of seconds since midnight and nanosecond.
447     ///
448     /// The nanosecond part is allowed to exceed 1,000,000,000 in order to represent a
449     /// [leap second](#leap-second-handling), but only when `secs % 60 == 59`.
450     ///
451     /// # Errors
452     ///
453     /// Returns `None` on invalid number of seconds and/or nanosecond.
454     ///
455     /// # Example
456     ///
457     /// ```
458     /// use chrono::NaiveTime;
459     ///
460     /// let from_nsecs_opt = NaiveTime::from_num_seconds_from_midnight_opt;
461     ///
462     /// assert!(from_nsecs_opt(0, 0).is_some());
463     /// assert!(from_nsecs_opt(86399, 999_999_999).is_some());
464     /// assert!(from_nsecs_opt(86399, 1_999_999_999).is_some()); // a leap second after 23:59:59
465     /// assert!(from_nsecs_opt(86_400, 0).is_none());
466     /// assert!(from_nsecs_opt(86399, 2_000_000_000).is_none());
467     /// ```
468     #[inline]
469     #[must_use]
from_num_seconds_from_midnight_opt(secs: u32, nano: u32) -> Option<NaiveTime>470     pub const fn from_num_seconds_from_midnight_opt(secs: u32, nano: u32) -> Option<NaiveTime> {
471         if secs >= 86_400 || nano >= 2_000_000_000 || (nano >= 1_000_000_000 && secs % 60 != 59) {
472             return None;
473         }
474         Some(NaiveTime { secs, frac: nano })
475     }
476 
477     /// Parses a string with the specified format string and returns a new `NaiveTime`.
478     /// See the [`format::strftime` module](crate::format::strftime)
479     /// on the supported escape sequences.
480     ///
481     /// # Example
482     ///
483     /// ```
484     /// use chrono::NaiveTime;
485     ///
486     /// let parse_from_str = NaiveTime::parse_from_str;
487     ///
488     /// assert_eq!(parse_from_str("23:56:04", "%H:%M:%S"),
489     ///            Ok(NaiveTime::from_hms_opt(23, 56, 4).unwrap()));
490     /// assert_eq!(parse_from_str("pm012345.6789", "%p%I%M%S%.f"),
491     ///            Ok(NaiveTime::from_hms_micro_opt(13, 23, 45, 678_900).unwrap()));
492     /// ```
493     ///
494     /// Date and offset is ignored for the purpose of parsing.
495     ///
496     /// ```
497     /// # use chrono::NaiveTime;
498     /// # let parse_from_str = NaiveTime::parse_from_str;
499     /// assert_eq!(parse_from_str("2014-5-17T12:34:56+09:30", "%Y-%m-%dT%H:%M:%S%z"),
500     ///            Ok(NaiveTime::from_hms_opt(12, 34, 56).unwrap()));
501     /// ```
502     ///
503     /// [Leap seconds](#leap-second-handling) are correctly handled by
504     /// treating any time of the form `hh:mm:60` as a leap second.
505     /// (This equally applies to the formatting, so the round trip is possible.)
506     ///
507     /// ```
508     /// # use chrono::NaiveTime;
509     /// # let parse_from_str = NaiveTime::parse_from_str;
510     /// assert_eq!(parse_from_str("08:59:60.123", "%H:%M:%S%.f"),
511     ///            Ok(NaiveTime::from_hms_milli_opt(8, 59, 59, 1_123).unwrap()));
512     /// ```
513     ///
514     /// Missing seconds are assumed to be zero,
515     /// but out-of-bound times or insufficient fields are errors otherwise.
516     ///
517     /// ```
518     /// # use chrono::NaiveTime;
519     /// # let parse_from_str = NaiveTime::parse_from_str;
520     /// assert_eq!(parse_from_str("7:15", "%H:%M"),
521     ///            Ok(NaiveTime::from_hms_opt(7, 15, 0).unwrap()));
522     ///
523     /// assert!(parse_from_str("04m33s", "%Mm%Ss").is_err());
524     /// assert!(parse_from_str("12", "%H").is_err());
525     /// assert!(parse_from_str("17:60", "%H:%M").is_err());
526     /// assert!(parse_from_str("24:00:00", "%H:%M:%S").is_err());
527     /// ```
528     ///
529     /// All parsed fields should be consistent to each other, otherwise it's an error.
530     /// Here `%H` is for 24-hour clocks, unlike `%I`,
531     /// and thus can be independently determined without AM/PM.
532     ///
533     /// ```
534     /// # use chrono::NaiveTime;
535     /// # let parse_from_str = NaiveTime::parse_from_str;
536     /// assert!(parse_from_str("13:07 AM", "%H:%M %p").is_err());
537     /// ```
parse_from_str(s: &str, fmt: &str) -> ParseResult<NaiveTime>538     pub fn parse_from_str(s: &str, fmt: &str) -> ParseResult<NaiveTime> {
539         let mut parsed = Parsed::new();
540         parse(&mut parsed, s, StrftimeItems::new(fmt))?;
541         parsed.to_naive_time()
542     }
543 
544     /// Parses a string from a user-specified format into a new `NaiveTime` value, and a slice with
545     /// the remaining portion of the string.
546     /// See the [`format::strftime` module](crate::format::strftime)
547     /// on the supported escape sequences.
548     ///
549     /// Similar to [`parse_from_str`](#method.parse_from_str).
550     ///
551     /// # Example
552     ///
553     /// ```rust
554     /// # use chrono::{NaiveTime};
555     /// let (time, remainder) = NaiveTime::parse_and_remainder(
556     ///     "3h4m33s trailing text", "%-Hh%-Mm%-Ss").unwrap();
557     /// assert_eq!(time, NaiveTime::from_hms_opt(3, 4, 33).unwrap());
558     /// assert_eq!(remainder, " trailing text");
559     /// ```
parse_and_remainder<'a>(s: &'a str, fmt: &str) -> ParseResult<(NaiveTime, &'a str)>560     pub fn parse_and_remainder<'a>(s: &'a str, fmt: &str) -> ParseResult<(NaiveTime, &'a str)> {
561         let mut parsed = Parsed::new();
562         let remainder = parse_and_remainder(&mut parsed, s, StrftimeItems::new(fmt))?;
563         parsed.to_naive_time().map(|t| (t, remainder))
564     }
565 
566     /// Adds given `TimeDelta` to the current time, and also returns the number of *seconds*
567     /// in the integral number of days ignored from the addition.
568     ///
569     /// # Example
570     ///
571     /// ```
572     /// use chrono::{TimeDelta, NaiveTime};
573     ///
574     /// let from_hms = |h, m, s| { NaiveTime::from_hms_opt(h, m, s).unwrap() };
575     ///
576     /// assert_eq!(from_hms(3, 4, 5).overflowing_add_signed(TimeDelta::hours(11)),
577     ///            (from_hms(14, 4, 5), 0));
578     /// assert_eq!(from_hms(3, 4, 5).overflowing_add_signed(TimeDelta::hours(23)),
579     ///            (from_hms(2, 4, 5), 86_400));
580     /// assert_eq!(from_hms(3, 4, 5).overflowing_add_signed(TimeDelta::hours(-7)),
581     ///            (from_hms(20, 4, 5), -86_400));
582     /// ```
583     #[must_use]
overflowing_add_signed(&self, rhs: TimeDelta) -> (NaiveTime, i64)584     pub const fn overflowing_add_signed(&self, rhs: TimeDelta) -> (NaiveTime, i64) {
585         let mut secs = self.secs as i64;
586         let mut frac = self.frac as i32;
587         let secs_to_add = rhs.num_seconds();
588         let frac_to_add = rhs.subsec_nanos();
589 
590         // Check if `self` is a leap second and adding `rhs` would escape that leap second.
591         // If that is the case, update `frac` and `secs` to involve no leap second.
592         // If it stays within the leap second or the second before, and only adds a fractional
593         // second, just do that and return (this way the rest of the code can ignore leap seconds).
594         if frac >= 1_000_000_000 {
595             // check below is adjusted to not overflow an i32: `frac + frac_to_add >= 2_000_000_000`
596             if secs_to_add > 0 || (frac_to_add > 0 && frac >= 2_000_000_000 - frac_to_add) {
597                 frac -= 1_000_000_000;
598             } else if secs_to_add < 0 {
599                 frac -= 1_000_000_000;
600                 secs += 1;
601             } else {
602                 return (NaiveTime { secs: self.secs, frac: (frac + frac_to_add) as u32 }, 0);
603             }
604         }
605 
606         let mut secs = secs + secs_to_add;
607         frac += frac_to_add;
608 
609         if frac < 0 {
610             frac += 1_000_000_000;
611             secs -= 1;
612         } else if frac >= 1_000_000_000 {
613             frac -= 1_000_000_000;
614             secs += 1;
615         }
616 
617         let secs_in_day = secs.rem_euclid(86_400);
618         let remaining = secs - secs_in_day;
619         (NaiveTime { secs: secs_in_day as u32, frac: frac as u32 }, remaining)
620     }
621 
622     /// Subtracts given `TimeDelta` from the current time, and also returns the number of *seconds*
623     /// in the integral number of days ignored from the subtraction.
624     ///
625     /// # Example
626     ///
627     /// ```
628     /// use chrono::{TimeDelta, NaiveTime};
629     ///
630     /// let from_hms = |h, m, s| { NaiveTime::from_hms_opt(h, m, s).unwrap() };
631     ///
632     /// assert_eq!(from_hms(3, 4, 5).overflowing_sub_signed(TimeDelta::hours(2)),
633     ///            (from_hms(1, 4, 5), 0));
634     /// assert_eq!(from_hms(3, 4, 5).overflowing_sub_signed(TimeDelta::hours(17)),
635     ///            (from_hms(10, 4, 5), 86_400));
636     /// assert_eq!(from_hms(3, 4, 5).overflowing_sub_signed(TimeDelta::hours(-22)),
637     ///            (from_hms(1, 4, 5), -86_400));
638     /// ```
639     #[inline]
640     #[must_use]
overflowing_sub_signed(&self, rhs: TimeDelta) -> (NaiveTime, i64)641     pub const fn overflowing_sub_signed(&self, rhs: TimeDelta) -> (NaiveTime, i64) {
642         let (time, rhs) = self.overflowing_add_signed(rhs.neg());
643         (time, -rhs) // safe to negate, rhs is within +/- (2^63 / 1000)
644     }
645 
646     /// Subtracts another `NaiveTime` from the current time.
647     /// Returns a `TimeDelta` within +/- 1 day.
648     /// This does not overflow or underflow at all.
649     ///
650     /// As a part of Chrono's [leap second handling](#leap-second-handling),
651     /// the subtraction assumes that **there is no leap second ever**,
652     /// except when any of the `NaiveTime`s themselves represents a leap second
653     /// in which case the assumption becomes that
654     /// **there are exactly one (or two) leap second(s) ever**.
655     ///
656     /// # Example
657     ///
658     /// ```
659     /// use chrono::{TimeDelta, NaiveTime};
660     ///
661     /// let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
662     /// let since = NaiveTime::signed_duration_since;
663     ///
664     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(3, 5, 7, 900)),
665     ///            TimeDelta::zero());
666     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(3, 5, 7, 875)),
667     ///            TimeDelta::milliseconds(25));
668     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(3, 5, 6, 925)),
669     ///            TimeDelta::milliseconds(975));
670     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(3, 5, 0, 900)),
671     ///            TimeDelta::seconds(7));
672     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(3, 0, 7, 900)),
673     ///            TimeDelta::seconds(5 * 60));
674     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(0, 5, 7, 900)),
675     ///            TimeDelta::seconds(3 * 3600));
676     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(4, 5, 7, 900)),
677     ///            TimeDelta::seconds(-3600));
678     /// assert_eq!(since(from_hmsm(3, 5, 7, 900), from_hmsm(2, 4, 6, 800)),
679     ///            TimeDelta::seconds(3600 + 60 + 1) + TimeDelta::milliseconds(100));
680     /// ```
681     ///
682     /// Leap seconds are handled, but the subtraction assumes that
683     /// there were no other leap seconds happened.
684     ///
685     /// ```
686     /// # use chrono::{TimeDelta, NaiveTime};
687     /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
688     /// # let since = NaiveTime::signed_duration_since;
689     /// assert_eq!(since(from_hmsm(3, 0, 59, 1_000), from_hmsm(3, 0, 59, 0)),
690     ///            TimeDelta::seconds(1));
691     /// assert_eq!(since(from_hmsm(3, 0, 59, 1_500), from_hmsm(3, 0, 59, 0)),
692     ///            TimeDelta::milliseconds(1500));
693     /// assert_eq!(since(from_hmsm(3, 0, 59, 1_000), from_hmsm(3, 0, 0, 0)),
694     ///            TimeDelta::seconds(60));
695     /// assert_eq!(since(from_hmsm(3, 0, 0, 0), from_hmsm(2, 59, 59, 1_000)),
696     ///            TimeDelta::seconds(1));
697     /// assert_eq!(since(from_hmsm(3, 0, 59, 1_000), from_hmsm(2, 59, 59, 1_000)),
698     ///            TimeDelta::seconds(61));
699     /// ```
700     #[must_use]
signed_duration_since(self, rhs: NaiveTime) -> TimeDelta701     pub const fn signed_duration_since(self, rhs: NaiveTime) -> TimeDelta {
702         //     |    |    :leap|    |    |    |    |    |    |    :leap|    |
703         //     |    |    :    |    |    |    |    |    |    |    :    |    |
704         // ----+----+-----*---+----+----+----+----+----+----+-------*-+----+----
705         //          |   `rhs` |                             |    `self`
706         //          |======================================>|       |
707         //          |     |  `self.secs - rhs.secs`         |`self.frac`
708         //          |====>|   |                             |======>|
709         //      `rhs.frac`|========================================>|
710         //          |     |   |        `self - rhs`         |       |
711 
712         let mut secs = self.secs as i64 - rhs.secs as i64;
713         let frac = self.frac as i64 - rhs.frac as i64;
714 
715         // `secs` may contain a leap second yet to be counted
716         if self.secs > rhs.secs && rhs.frac >= 1_000_000_000 {
717             secs += 1;
718         } else if self.secs < rhs.secs && self.frac >= 1_000_000_000 {
719             secs -= 1;
720         }
721 
722         let secs_from_frac = frac.div_euclid(1_000_000_000);
723         let frac = frac.rem_euclid(1_000_000_000) as u32;
724 
725         expect!(TimeDelta::new(secs + secs_from_frac, frac), "must be in range")
726     }
727 
728     /// Adds given `FixedOffset` to the current time, and returns the number of days that should be
729     /// added to a date as a result of the offset (either `-1`, `0`, or `1` because the offset is
730     /// always less than 24h).
731     ///
732     /// This method is similar to [`overflowing_add_signed`](#method.overflowing_add_signed), but
733     /// preserves leap seconds.
overflowing_add_offset(&self, offset: FixedOffset) -> (NaiveTime, i32)734     pub(super) const fn overflowing_add_offset(&self, offset: FixedOffset) -> (NaiveTime, i32) {
735         let secs = self.secs as i32 + offset.local_minus_utc();
736         let days = secs.div_euclid(86_400);
737         let secs = secs.rem_euclid(86_400);
738         (NaiveTime { secs: secs as u32, frac: self.frac }, days)
739     }
740 
741     /// Subtracts given `FixedOffset` from the current time, and returns the number of days that
742     /// should be added to a date as a result of the offset (either `-1`, `0`, or `1` because the
743     /// offset is always less than 24h).
744     ///
745     /// This method is similar to [`overflowing_sub_signed`](#method.overflowing_sub_signed), but
746     /// preserves leap seconds.
overflowing_sub_offset(&self, offset: FixedOffset) -> (NaiveTime, i32)747     pub(super) const fn overflowing_sub_offset(&self, offset: FixedOffset) -> (NaiveTime, i32) {
748         let secs = self.secs as i32 - offset.local_minus_utc();
749         let days = secs.div_euclid(86_400);
750         let secs = secs.rem_euclid(86_400);
751         (NaiveTime { secs: secs as u32, frac: self.frac }, days)
752     }
753 
754     /// Formats the time with the specified formatting items.
755     /// Otherwise it is the same as the ordinary [`format`](#method.format) method.
756     ///
757     /// The `Iterator` of items should be `Clone`able,
758     /// since the resulting `DelayedFormat` value may be formatted multiple times.
759     ///
760     /// # Example
761     ///
762     /// ```
763     /// use chrono::NaiveTime;
764     /// use chrono::format::strftime::StrftimeItems;
765     ///
766     /// let fmt = StrftimeItems::new("%H:%M:%S");
767     /// let t = NaiveTime::from_hms_opt(23, 56, 4).unwrap();
768     /// assert_eq!(t.format_with_items(fmt.clone()).to_string(), "23:56:04");
769     /// assert_eq!(t.format("%H:%M:%S").to_string(),             "23:56:04");
770     /// ```
771     ///
772     /// The resulting `DelayedFormat` can be formatted directly via the `Display` trait.
773     ///
774     /// ```
775     /// # use chrono::NaiveTime;
776     /// # use chrono::format::strftime::StrftimeItems;
777     /// # let fmt = StrftimeItems::new("%H:%M:%S").clone();
778     /// # let t = NaiveTime::from_hms_opt(23, 56, 4).unwrap();
779     /// assert_eq!(format!("{}", t.format_with_items(fmt)), "23:56:04");
780     /// ```
781     #[cfg(feature = "alloc")]
782     #[inline]
783     #[must_use]
format_with_items<'a, I, B>(&self, items: I) -> DelayedFormat<I> where I: Iterator<Item = B> + Clone, B: Borrow<Item<'a>>,784     pub fn format_with_items<'a, I, B>(&self, items: I) -> DelayedFormat<I>
785     where
786         I: Iterator<Item = B> + Clone,
787         B: Borrow<Item<'a>>,
788     {
789         DelayedFormat::new(None, Some(*self), items)
790     }
791 
792     /// Formats the time with the specified format string.
793     /// See the [`format::strftime` module](crate::format::strftime)
794     /// on the supported escape sequences.
795     ///
796     /// This returns a `DelayedFormat`,
797     /// which gets converted to a string only when actual formatting happens.
798     /// You may use the `to_string` method to get a `String`,
799     /// or just feed it into `print!` and other formatting macros.
800     /// (In this way it avoids the redundant memory allocation.)
801     ///
802     /// A wrong format string does *not* issue an error immediately.
803     /// Rather, converting or formatting the `DelayedFormat` fails.
804     /// You are recommended to immediately use `DelayedFormat` for this reason.
805     ///
806     /// # Example
807     ///
808     /// ```
809     /// use chrono::NaiveTime;
810     ///
811     /// let t = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
812     /// assert_eq!(t.format("%H:%M:%S").to_string(), "23:56:04");
813     /// assert_eq!(t.format("%H:%M:%S%.6f").to_string(), "23:56:04.012345");
814     /// assert_eq!(t.format("%-I:%M %p").to_string(), "11:56 PM");
815     /// ```
816     ///
817     /// The resulting `DelayedFormat` can be formatted directly via the `Display` trait.
818     ///
819     /// ```
820     /// # use chrono::NaiveTime;
821     /// # let t = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
822     /// assert_eq!(format!("{}", t.format("%H:%M:%S")), "23:56:04");
823     /// assert_eq!(format!("{}", t.format("%H:%M:%S%.6f")), "23:56:04.012345");
824     /// assert_eq!(format!("{}", t.format("%-I:%M %p")), "11:56 PM");
825     /// ```
826     #[cfg(feature = "alloc")]
827     #[inline]
828     #[must_use]
format<'a>(&self, fmt: &'a str) -> DelayedFormat<StrftimeItems<'a>>829     pub fn format<'a>(&self, fmt: &'a str) -> DelayedFormat<StrftimeItems<'a>> {
830         self.format_with_items(StrftimeItems::new(fmt))
831     }
832 
833     /// Returns a triple of the hour, minute and second numbers.
hms(&self) -> (u32, u32, u32)834     pub(crate) fn hms(&self) -> (u32, u32, u32) {
835         let sec = self.secs % 60;
836         let mins = self.secs / 60;
837         let min = mins % 60;
838         let hour = mins / 60;
839         (hour, min, sec)
840     }
841 
842     /// Returns the number of non-leap seconds past the last midnight.
843     // This duplicates `Timelike::num_seconds_from_midnight()`, because trait methods can't be const
844     // yet.
845     #[inline]
num_seconds_from_midnight(&self) -> u32846     pub(crate) const fn num_seconds_from_midnight(&self) -> u32 {
847         self.secs
848     }
849 
850     /// Returns the number of nanoseconds since the whole non-leap second.
851     // This duplicates `Timelike::nanosecond()`, because trait methods can't be const yet.
852     #[inline]
nanosecond(&self) -> u32853     pub(crate) const fn nanosecond(&self) -> u32 {
854         self.frac
855     }
856 
857     /// The earliest possible `NaiveTime`
858     pub const MIN: Self = Self { secs: 0, frac: 0 };
859     pub(super) const MAX: Self = Self { secs: 23 * 3600 + 59 * 60 + 59, frac: 999_999_999 };
860 }
861 
862 impl Timelike for NaiveTime {
863     /// Returns the hour number from 0 to 23.
864     ///
865     /// # Example
866     ///
867     /// ```
868     /// use chrono::{NaiveTime, Timelike};
869     ///
870     /// assert_eq!(NaiveTime::from_hms_opt(0, 0, 0).unwrap().hour(), 0);
871     /// assert_eq!(NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap().hour(), 23);
872     /// ```
873     #[inline]
hour(&self) -> u32874     fn hour(&self) -> u32 {
875         self.hms().0
876     }
877 
878     /// Returns the minute number from 0 to 59.
879     ///
880     /// # Example
881     ///
882     /// ```
883     /// use chrono::{NaiveTime, Timelike};
884     ///
885     /// assert_eq!(NaiveTime::from_hms_opt(0, 0, 0).unwrap().minute(), 0);
886     /// assert_eq!(NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap().minute(), 56);
887     /// ```
888     #[inline]
minute(&self) -> u32889     fn minute(&self) -> u32 {
890         self.hms().1
891     }
892 
893     /// Returns the second number from 0 to 59.
894     ///
895     /// # Example
896     ///
897     /// ```
898     /// use chrono::{NaiveTime, Timelike};
899     ///
900     /// assert_eq!(NaiveTime::from_hms_opt(0, 0, 0).unwrap().second(), 0);
901     /// assert_eq!(NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap().second(), 4);
902     /// ```
903     ///
904     /// This method never returns 60 even when it is a leap second.
905     /// ([Why?](#leap-second-handling))
906     /// Use the proper [formatting method](#method.format) to get a human-readable representation.
907     ///
908     #[cfg_attr(not(feature = "std"), doc = "```ignore")]
909     #[cfg_attr(feature = "std", doc = "```")]
910     /// # use chrono::{NaiveTime, Timelike};
911     /// let leap = NaiveTime::from_hms_milli_opt(23, 59, 59, 1_000).unwrap();
912     /// assert_eq!(leap.second(), 59);
913     /// assert_eq!(leap.format("%H:%M:%S").to_string(), "23:59:60");
914     /// ```
915     #[inline]
second(&self) -> u32916     fn second(&self) -> u32 {
917         self.hms().2
918     }
919 
920     /// Returns the number of nanoseconds since the whole non-leap second.
921     /// The range from 1,000,000,000 to 1,999,999,999 represents
922     /// the [leap second](#leap-second-handling).
923     ///
924     /// # Example
925     ///
926     /// ```
927     /// use chrono::{NaiveTime, Timelike};
928     ///
929     /// assert_eq!(NaiveTime::from_hms_opt(0, 0, 0).unwrap().nanosecond(), 0);
930     /// assert_eq!(NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap().nanosecond(), 12_345_678);
931     /// ```
932     ///
933     /// Leap seconds may have seemingly out-of-range return values.
934     /// You can reduce the range with `time.nanosecond() % 1_000_000_000`, or
935     /// use the proper [formatting method](#method.format) to get a human-readable representation.
936     ///
937     #[cfg_attr(not(feature = "std"), doc = "```ignore")]
938     #[cfg_attr(feature = "std", doc = "```")]
939     /// # use chrono::{NaiveTime, Timelike};
940     /// let leap = NaiveTime::from_hms_milli_opt(23, 59, 59, 1_000).unwrap();
941     /// assert_eq!(leap.nanosecond(), 1_000_000_000);
942     /// assert_eq!(leap.format("%H:%M:%S%.9f").to_string(), "23:59:60.000000000");
943     /// ```
944     #[inline]
nanosecond(&self) -> u32945     fn nanosecond(&self) -> u32 {
946         self.frac
947     }
948 
949     /// Makes a new `NaiveTime` with the hour number changed.
950     ///
951     /// # Errors
952     ///
953     /// Returns `None` if the value for `hour` is invalid.
954     ///
955     /// # Example
956     ///
957     /// ```
958     /// use chrono::{NaiveTime, Timelike};
959     ///
960     /// let dt = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
961     /// assert_eq!(dt.with_hour(7), Some(NaiveTime::from_hms_nano_opt(7, 56, 4, 12_345_678).unwrap()));
962     /// assert_eq!(dt.with_hour(24), None);
963     /// ```
964     #[inline]
with_hour(&self, hour: u32) -> Option<NaiveTime>965     fn with_hour(&self, hour: u32) -> Option<NaiveTime> {
966         if hour >= 24 {
967             return None;
968         }
969         let secs = hour * 3600 + self.secs % 3600;
970         Some(NaiveTime { secs, ..*self })
971     }
972 
973     /// Makes a new `NaiveTime` with the minute number changed.
974     ///
975     /// # Errors
976     ///
977     /// Returns `None` if the value for `minute` is invalid.
978     ///
979     /// # Example
980     ///
981     /// ```
982     /// use chrono::{NaiveTime, Timelike};
983     ///
984     /// let dt = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
985     /// assert_eq!(dt.with_minute(45), Some(NaiveTime::from_hms_nano_opt(23, 45, 4, 12_345_678).unwrap()));
986     /// assert_eq!(dt.with_minute(60), None);
987     /// ```
988     #[inline]
with_minute(&self, min: u32) -> Option<NaiveTime>989     fn with_minute(&self, min: u32) -> Option<NaiveTime> {
990         if min >= 60 {
991             return None;
992         }
993         let secs = self.secs / 3600 * 3600 + min * 60 + self.secs % 60;
994         Some(NaiveTime { secs, ..*self })
995     }
996 
997     /// Makes a new `NaiveTime` with the second number changed.
998     ///
999     /// As with the [`second`](#method.second) method,
1000     /// the input range is restricted to 0 through 59.
1001     ///
1002     /// # Errors
1003     ///
1004     /// Returns `None` if the value for `second` is invalid.
1005     ///
1006     /// # Example
1007     ///
1008     /// ```
1009     /// use chrono::{NaiveTime, Timelike};
1010     ///
1011     /// let dt = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
1012     /// assert_eq!(dt.with_second(17), Some(NaiveTime::from_hms_nano_opt(23, 56, 17, 12_345_678).unwrap()));
1013     /// assert_eq!(dt.with_second(60), None);
1014     /// ```
1015     #[inline]
with_second(&self, sec: u32) -> Option<NaiveTime>1016     fn with_second(&self, sec: u32) -> Option<NaiveTime> {
1017         if sec >= 60 {
1018             return None;
1019         }
1020         let secs = self.secs / 60 * 60 + sec;
1021         Some(NaiveTime { secs, ..*self })
1022     }
1023 
1024     /// Makes a new `NaiveTime` with nanoseconds since the whole non-leap second changed.
1025     ///
1026     /// As with the [`nanosecond`](#method.nanosecond) method,
1027     /// the input range can exceed 1,000,000,000 for leap seconds.
1028     ///
1029     /// # Errors
1030     ///
1031     /// Returns `None` if `nanosecond >= 2,000,000,000`.
1032     ///
1033     /// # Example
1034     ///
1035     /// ```
1036     /// use chrono::{NaiveTime, Timelike};
1037     ///
1038     /// let dt = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
1039     /// assert_eq!(dt.with_nanosecond(333_333_333),
1040     ///            Some(NaiveTime::from_hms_nano_opt(23, 56, 4, 333_333_333).unwrap()));
1041     /// assert_eq!(dt.with_nanosecond(2_000_000_000), None);
1042     /// ```
1043     ///
1044     /// Leap seconds can theoretically follow *any* whole second.
1045     /// The following would be a proper leap second at the time zone offset of UTC-00:03:57
1046     /// (there are several historical examples comparable to this "non-sense" offset),
1047     /// and therefore is allowed.
1048     ///
1049     /// ```
1050     /// # use chrono::{NaiveTime, Timelike};
1051     /// let dt = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
1052     /// let strange_leap_second = dt.with_nanosecond(1_333_333_333).unwrap();
1053     /// assert_eq!(strange_leap_second.nanosecond(), 1_333_333_333);
1054     /// ```
1055     #[inline]
with_nanosecond(&self, nano: u32) -> Option<NaiveTime>1056     fn with_nanosecond(&self, nano: u32) -> Option<NaiveTime> {
1057         if nano >= 2_000_000_000 {
1058             return None;
1059         }
1060         Some(NaiveTime { frac: nano, ..*self })
1061     }
1062 
1063     /// Returns the number of non-leap seconds past the last midnight.
1064     ///
1065     /// # Example
1066     ///
1067     /// ```
1068     /// use chrono::{NaiveTime, Timelike};
1069     ///
1070     /// assert_eq!(NaiveTime::from_hms_opt(1, 2, 3).unwrap().num_seconds_from_midnight(),
1071     ///            3723);
1072     /// assert_eq!(NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap().num_seconds_from_midnight(),
1073     ///            86164);
1074     /// assert_eq!(NaiveTime::from_hms_milli_opt(23, 59, 59, 1_000).unwrap().num_seconds_from_midnight(),
1075     ///            86399);
1076     /// ```
1077     #[inline]
num_seconds_from_midnight(&self) -> u321078     fn num_seconds_from_midnight(&self) -> u32 {
1079         self.secs // do not repeat the calculation!
1080     }
1081 }
1082 
1083 /// Add `TimeDelta` to `NaiveTime`.
1084 ///
1085 /// This wraps around and never overflows or underflows.
1086 /// In particular the addition ignores integral number of days.
1087 ///
1088 /// As a part of Chrono's [leap second handling], the addition assumes that **there is no leap
1089 /// second ever**, except when the `NaiveTime` itself represents a leap second in which case the
1090 /// assumption becomes that **there is exactly a single leap second ever**.
1091 ///
1092 /// # Example
1093 ///
1094 /// ```
1095 /// use chrono::{TimeDelta, NaiveTime};
1096 ///
1097 /// let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1098 ///
1099 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::zero(),                  from_hmsm(3, 5, 7, 0));
1100 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(1),              from_hmsm(3, 5, 8, 0));
1101 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(-1),             from_hmsm(3, 5, 6, 0));
1102 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(60 + 4),         from_hmsm(3, 6, 11, 0));
1103 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(7*60*60 - 6*60), from_hmsm(9, 59, 7, 0));
1104 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::milliseconds(80),        from_hmsm(3, 5, 7, 80));
1105 /// assert_eq!(from_hmsm(3, 5, 7, 950) + TimeDelta::milliseconds(280),     from_hmsm(3, 5, 8, 230));
1106 /// assert_eq!(from_hmsm(3, 5, 7, 950) + TimeDelta::milliseconds(-980),    from_hmsm(3, 5, 6, 970));
1107 /// ```
1108 ///
1109 /// The addition wraps around.
1110 ///
1111 /// ```
1112 /// # use chrono::{TimeDelta, NaiveTime};
1113 /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1114 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(22*60*60), from_hmsm(1, 5, 7, 0));
1115 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::seconds(-8*60*60), from_hmsm(19, 5, 7, 0));
1116 /// assert_eq!(from_hmsm(3, 5, 7, 0) + TimeDelta::days(800),         from_hmsm(3, 5, 7, 0));
1117 /// ```
1118 ///
1119 /// Leap seconds are handled, but the addition assumes that it is the only leap second happened.
1120 ///
1121 /// ```
1122 /// # use chrono::{TimeDelta, NaiveTime};
1123 /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1124 /// let leap = from_hmsm(3, 5, 59, 1_300);
1125 /// assert_eq!(leap + TimeDelta::zero(),             from_hmsm(3, 5, 59, 1_300));
1126 /// assert_eq!(leap + TimeDelta::milliseconds(-500), from_hmsm(3, 5, 59, 800));
1127 /// assert_eq!(leap + TimeDelta::milliseconds(500),  from_hmsm(3, 5, 59, 1_800));
1128 /// assert_eq!(leap + TimeDelta::milliseconds(800),  from_hmsm(3, 6, 0, 100));
1129 /// assert_eq!(leap + TimeDelta::seconds(10),        from_hmsm(3, 6, 9, 300));
1130 /// assert_eq!(leap + TimeDelta::seconds(-10),       from_hmsm(3, 5, 50, 300));
1131 /// assert_eq!(leap + TimeDelta::days(1),            from_hmsm(3, 5, 59, 300));
1132 /// ```
1133 ///
1134 /// [leap second handling]: crate::NaiveTime#leap-second-handling
1135 impl Add<TimeDelta> for NaiveTime {
1136     type Output = NaiveTime;
1137 
1138     #[inline]
add(self, rhs: TimeDelta) -> NaiveTime1139     fn add(self, rhs: TimeDelta) -> NaiveTime {
1140         self.overflowing_add_signed(rhs).0
1141     }
1142 }
1143 
1144 /// Add-assign `TimeDelta` to `NaiveTime`.
1145 ///
1146 /// This wraps around and never overflows or underflows.
1147 /// In particular the addition ignores integral number of days.
1148 impl AddAssign<TimeDelta> for NaiveTime {
1149     #[inline]
add_assign(&mut self, rhs: TimeDelta)1150     fn add_assign(&mut self, rhs: TimeDelta) {
1151         *self = self.add(rhs);
1152     }
1153 }
1154 
1155 /// Add `std::time::Duration` to `NaiveTime`.
1156 ///
1157 /// This wraps around and never overflows or underflows.
1158 /// In particular the addition ignores integral number of days.
1159 impl Add<Duration> for NaiveTime {
1160     type Output = NaiveTime;
1161 
1162     #[inline]
add(self, rhs: Duration) -> NaiveTime1163     fn add(self, rhs: Duration) -> NaiveTime {
1164         // We don't care about values beyond `24 * 60 * 60`, so we can take a modulus and avoid
1165         // overflow during the conversion to `TimeDelta`.
1166         // But we limit to double that just in case `self` is a leap-second.
1167         let secs = rhs.as_secs() % (2 * 24 * 60 * 60);
1168         let d = TimeDelta::new(secs as i64, rhs.subsec_nanos()).unwrap();
1169         self.overflowing_add_signed(d).0
1170     }
1171 }
1172 
1173 /// Add-assign `std::time::Duration` to `NaiveTime`.
1174 ///
1175 /// This wraps around and never overflows or underflows.
1176 /// In particular the addition ignores integral number of days.
1177 impl AddAssign<Duration> for NaiveTime {
1178     #[inline]
add_assign(&mut self, rhs: Duration)1179     fn add_assign(&mut self, rhs: Duration) {
1180         *self = *self + rhs;
1181     }
1182 }
1183 
1184 /// Add `FixedOffset` to `NaiveTime`.
1185 ///
1186 /// This wraps around and never overflows or underflows.
1187 /// In particular the addition ignores integral number of days.
1188 impl Add<FixedOffset> for NaiveTime {
1189     type Output = NaiveTime;
1190 
1191     #[inline]
add(self, rhs: FixedOffset) -> NaiveTime1192     fn add(self, rhs: FixedOffset) -> NaiveTime {
1193         self.overflowing_add_offset(rhs).0
1194     }
1195 }
1196 
1197 /// Subtract `TimeDelta` from `NaiveTime`.
1198 ///
1199 /// This wraps around and never overflows or underflows.
1200 /// In particular the subtraction ignores integral number of days.
1201 /// This is the same as addition with a negated `TimeDelta`.
1202 ///
1203 /// As a part of Chrono's [leap second handling], the subtraction assumes that **there is no leap
1204 /// second ever**, except when the `NaiveTime` itself represents a leap second in which case the
1205 /// assumption becomes that **there is exactly a single leap second ever**.
1206 ///
1207 /// # Example
1208 ///
1209 /// ```
1210 /// use chrono::{TimeDelta, NaiveTime};
1211 ///
1212 /// let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1213 ///
1214 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::zero(),                  from_hmsm(3, 5, 7, 0));
1215 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::seconds(1),              from_hmsm(3, 5, 6, 0));
1216 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::seconds(60 + 5),         from_hmsm(3, 4, 2, 0));
1217 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::seconds(2*60*60 + 6*60), from_hmsm(0, 59, 7, 0));
1218 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::milliseconds(80),        from_hmsm(3, 5, 6, 920));
1219 /// assert_eq!(from_hmsm(3, 5, 7, 950) - TimeDelta::milliseconds(280),     from_hmsm(3, 5, 7, 670));
1220 /// ```
1221 ///
1222 /// The subtraction wraps around.
1223 ///
1224 /// ```
1225 /// # use chrono::{TimeDelta, NaiveTime};
1226 /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1227 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::seconds(8*60*60), from_hmsm(19, 5, 7, 0));
1228 /// assert_eq!(from_hmsm(3, 5, 7, 0) - TimeDelta::days(800),        from_hmsm(3, 5, 7, 0));
1229 /// ```
1230 ///
1231 /// Leap seconds are handled, but the subtraction assumes that it is the only leap second happened.
1232 ///
1233 /// ```
1234 /// # use chrono::{TimeDelta, NaiveTime};
1235 /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1236 /// let leap = from_hmsm(3, 5, 59, 1_300);
1237 /// assert_eq!(leap - TimeDelta::zero(),            from_hmsm(3, 5, 59, 1_300));
1238 /// assert_eq!(leap - TimeDelta::milliseconds(200), from_hmsm(3, 5, 59, 1_100));
1239 /// assert_eq!(leap - TimeDelta::milliseconds(500), from_hmsm(3, 5, 59, 800));
1240 /// assert_eq!(leap - TimeDelta::seconds(60),       from_hmsm(3, 5, 0, 300));
1241 /// assert_eq!(leap - TimeDelta::days(1),           from_hmsm(3, 6, 0, 300));
1242 /// ```
1243 ///
1244 /// [leap second handling]: crate::NaiveTime#leap-second-handling
1245 impl Sub<TimeDelta> for NaiveTime {
1246     type Output = NaiveTime;
1247 
1248     #[inline]
sub(self, rhs: TimeDelta) -> NaiveTime1249     fn sub(self, rhs: TimeDelta) -> NaiveTime {
1250         self.overflowing_sub_signed(rhs).0
1251     }
1252 }
1253 
1254 /// Subtract-assign `TimeDelta` from `NaiveTime`.
1255 ///
1256 /// This wraps around and never overflows or underflows.
1257 /// In particular the subtraction ignores integral number of days.
1258 impl SubAssign<TimeDelta> for NaiveTime {
1259     #[inline]
sub_assign(&mut self, rhs: TimeDelta)1260     fn sub_assign(&mut self, rhs: TimeDelta) {
1261         *self = self.sub(rhs);
1262     }
1263 }
1264 
1265 /// Subtract `std::time::Duration` from `NaiveTime`.
1266 ///
1267 /// This wraps around and never overflows or underflows.
1268 /// In particular the subtraction ignores integral number of days.
1269 impl Sub<Duration> for NaiveTime {
1270     type Output = NaiveTime;
1271 
1272     #[inline]
sub(self, rhs: Duration) -> NaiveTime1273     fn sub(self, rhs: Duration) -> NaiveTime {
1274         // We don't care about values beyond `24 * 60 * 60`, so we can take a modulus and avoid
1275         // overflow during the conversion to `TimeDelta`.
1276         // But we limit to double that just in case `self` is a leap-second.
1277         let secs = rhs.as_secs() % (2 * 24 * 60 * 60);
1278         let d = TimeDelta::new(secs as i64, rhs.subsec_nanos()).unwrap();
1279         self.overflowing_sub_signed(d).0
1280     }
1281 }
1282 
1283 /// Subtract-assign `std::time::Duration` from `NaiveTime`.
1284 ///
1285 /// This wraps around and never overflows or underflows.
1286 /// In particular the subtraction ignores integral number of days.
1287 impl SubAssign<Duration> for NaiveTime {
1288     #[inline]
sub_assign(&mut self, rhs: Duration)1289     fn sub_assign(&mut self, rhs: Duration) {
1290         *self = *self - rhs;
1291     }
1292 }
1293 
1294 /// Subtract `FixedOffset` from `NaiveTime`.
1295 ///
1296 /// This wraps around and never overflows or underflows.
1297 /// In particular the subtraction ignores integral number of days.
1298 impl Sub<FixedOffset> for NaiveTime {
1299     type Output = NaiveTime;
1300 
1301     #[inline]
sub(self, rhs: FixedOffset) -> NaiveTime1302     fn sub(self, rhs: FixedOffset) -> NaiveTime {
1303         self.overflowing_sub_offset(rhs).0
1304     }
1305 }
1306 
1307 /// Subtracts another `NaiveTime` from the current time.
1308 /// Returns a `TimeDelta` within +/- 1 day.
1309 /// This does not overflow or underflow at all.
1310 ///
1311 /// As a part of Chrono's [leap second handling](#leap-second-handling),
1312 /// the subtraction assumes that **there is no leap second ever**,
1313 /// except when any of the `NaiveTime`s themselves represents a leap second
1314 /// in which case the assumption becomes that
1315 /// **there are exactly one (or two) leap second(s) ever**.
1316 ///
1317 /// The implementation is a wrapper around
1318 /// [`NaiveTime::signed_duration_since`](#method.signed_duration_since).
1319 ///
1320 /// # Example
1321 ///
1322 /// ```
1323 /// use chrono::{TimeDelta, NaiveTime};
1324 ///
1325 /// let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1326 ///
1327 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(3, 5, 7, 900), TimeDelta::zero());
1328 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(3, 5, 7, 875), TimeDelta::milliseconds(25));
1329 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(3, 5, 6, 925), TimeDelta::milliseconds(975));
1330 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(3, 5, 0, 900), TimeDelta::seconds(7));
1331 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(3, 0, 7, 900), TimeDelta::seconds(5 * 60));
1332 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(0, 5, 7, 900), TimeDelta::seconds(3 * 3600));
1333 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(4, 5, 7, 900), TimeDelta::seconds(-3600));
1334 /// assert_eq!(from_hmsm(3, 5, 7, 900) - from_hmsm(2, 4, 6, 800),
1335 ///            TimeDelta::seconds(3600 + 60 + 1) + TimeDelta::milliseconds(100));
1336 /// ```
1337 ///
1338 /// Leap seconds are handled, but the subtraction assumes that
1339 /// there were no other leap seconds happened.
1340 ///
1341 /// ```
1342 /// # use chrono::{TimeDelta, NaiveTime};
1343 /// # let from_hmsm = |h, m, s, milli| { NaiveTime::from_hms_milli_opt(h, m, s, milli).unwrap() };
1344 /// assert_eq!(from_hmsm(3, 0, 59, 1_000) - from_hmsm(3, 0, 59, 0), TimeDelta::seconds(1));
1345 /// assert_eq!(from_hmsm(3, 0, 59, 1_500) - from_hmsm(3, 0, 59, 0),
1346 ///            TimeDelta::milliseconds(1500));
1347 /// assert_eq!(from_hmsm(3, 0, 59, 1_000) - from_hmsm(3, 0, 0, 0), TimeDelta::seconds(60));
1348 /// assert_eq!(from_hmsm(3, 0, 0, 0) - from_hmsm(2, 59, 59, 1_000), TimeDelta::seconds(1));
1349 /// assert_eq!(from_hmsm(3, 0, 59, 1_000) - from_hmsm(2, 59, 59, 1_000),
1350 ///            TimeDelta::seconds(61));
1351 /// ```
1352 impl Sub<NaiveTime> for NaiveTime {
1353     type Output = TimeDelta;
1354 
1355     #[inline]
sub(self, rhs: NaiveTime) -> TimeDelta1356     fn sub(self, rhs: NaiveTime) -> TimeDelta {
1357         self.signed_duration_since(rhs)
1358     }
1359 }
1360 
1361 /// The `Debug` output of the naive time `t` is the same as
1362 /// [`t.format("%H:%M:%S%.f")`](crate::format::strftime).
1363 ///
1364 /// The string printed can be readily parsed via the `parse` method on `str`.
1365 ///
1366 /// It should be noted that, for leap seconds not on the minute boundary,
1367 /// it may print a representation not distinguishable from non-leap seconds.
1368 /// This doesn't matter in practice, since such leap seconds never happened.
1369 /// (By the time of the first leap second on 1972-06-30,
1370 /// every time zone offset around the world has standardized to the 5-minute alignment.)
1371 ///
1372 /// # Example
1373 ///
1374 /// ```
1375 /// use chrono::NaiveTime;
1376 ///
1377 /// assert_eq!(format!("{:?}", NaiveTime::from_hms_opt(23, 56, 4).unwrap()),              "23:56:04");
1378 /// assert_eq!(format!("{:?}", NaiveTime::from_hms_milli_opt(23, 56, 4, 12).unwrap()),    "23:56:04.012");
1379 /// assert_eq!(format!("{:?}", NaiveTime::from_hms_micro_opt(23, 56, 4, 1234).unwrap()),  "23:56:04.001234");
1380 /// assert_eq!(format!("{:?}", NaiveTime::from_hms_nano_opt(23, 56, 4, 123456).unwrap()), "23:56:04.000123456");
1381 /// ```
1382 ///
1383 /// Leap seconds may also be used.
1384 ///
1385 /// ```
1386 /// # use chrono::NaiveTime;
1387 /// assert_eq!(format!("{:?}", NaiveTime::from_hms_milli_opt(6, 59, 59, 1_500).unwrap()), "06:59:60.500");
1388 /// ```
1389 impl fmt::Debug for NaiveTime {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result1390     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1391         let (hour, min, sec) = self.hms();
1392         let (sec, nano) = if self.frac >= 1_000_000_000 {
1393             (sec + 1, self.frac - 1_000_000_000)
1394         } else {
1395             (sec, self.frac)
1396         };
1397 
1398         use core::fmt::Write;
1399         write_hundreds(f, hour as u8)?;
1400         f.write_char(':')?;
1401         write_hundreds(f, min as u8)?;
1402         f.write_char(':')?;
1403         write_hundreds(f, sec as u8)?;
1404 
1405         if nano == 0 {
1406             Ok(())
1407         } else if nano % 1_000_000 == 0 {
1408             write!(f, ".{:03}", nano / 1_000_000)
1409         } else if nano % 1_000 == 0 {
1410             write!(f, ".{:06}", nano / 1_000)
1411         } else {
1412             write!(f, ".{:09}", nano)
1413         }
1414     }
1415 }
1416 
1417 /// The `Display` output of the naive time `t` is the same as
1418 /// [`t.format("%H:%M:%S%.f")`](crate::format::strftime).
1419 ///
1420 /// The string printed can be readily parsed via the `parse` method on `str`.
1421 ///
1422 /// It should be noted that, for leap seconds not on the minute boundary,
1423 /// it may print a representation not distinguishable from non-leap seconds.
1424 /// This doesn't matter in practice, since such leap seconds never happened.
1425 /// (By the time of the first leap second on 1972-06-30,
1426 /// every time zone offset around the world has standardized to the 5-minute alignment.)
1427 ///
1428 /// # Example
1429 ///
1430 /// ```
1431 /// use chrono::NaiveTime;
1432 ///
1433 /// assert_eq!(format!("{}", NaiveTime::from_hms_opt(23, 56, 4).unwrap()),              "23:56:04");
1434 /// assert_eq!(format!("{}", NaiveTime::from_hms_milli_opt(23, 56, 4, 12).unwrap()),    "23:56:04.012");
1435 /// assert_eq!(format!("{}", NaiveTime::from_hms_micro_opt(23, 56, 4, 1234).unwrap()),  "23:56:04.001234");
1436 /// assert_eq!(format!("{}", NaiveTime::from_hms_nano_opt(23, 56, 4, 123456).unwrap()), "23:56:04.000123456");
1437 /// ```
1438 ///
1439 /// Leap seconds may also be used.
1440 ///
1441 /// ```
1442 /// # use chrono::NaiveTime;
1443 /// assert_eq!(format!("{}", NaiveTime::from_hms_milli_opt(6, 59, 59, 1_500).unwrap()), "06:59:60.500");
1444 /// ```
1445 impl fmt::Display for NaiveTime {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result1446     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1447         fmt::Debug::fmt(self, f)
1448     }
1449 }
1450 
1451 /// Parsing a `str` into a `NaiveTime` uses the same format,
1452 /// [`%H:%M:%S%.f`](crate::format::strftime), as in `Debug` and `Display`.
1453 ///
1454 /// # Example
1455 ///
1456 /// ```
1457 /// use chrono::NaiveTime;
1458 ///
1459 /// let t = NaiveTime::from_hms_opt(23, 56, 4).unwrap();
1460 /// assert_eq!("23:56:04".parse::<NaiveTime>(), Ok(t));
1461 ///
1462 /// let t = NaiveTime::from_hms_nano_opt(23, 56, 4, 12_345_678).unwrap();
1463 /// assert_eq!("23:56:4.012345678".parse::<NaiveTime>(), Ok(t));
1464 ///
1465 /// let t = NaiveTime::from_hms_nano_opt(23, 59, 59, 1_234_567_890).unwrap(); // leap second
1466 /// assert_eq!("23:59:60.23456789".parse::<NaiveTime>(), Ok(t));
1467 ///
1468 /// // Seconds are optional
1469 /// let t = NaiveTime::from_hms_opt(23, 56, 0).unwrap();
1470 /// assert_eq!("23:56".parse::<NaiveTime>(), Ok(t));
1471 ///
1472 /// assert!("foo".parse::<NaiveTime>().is_err());
1473 /// ```
1474 impl str::FromStr for NaiveTime {
1475     type Err = ParseError;
1476 
from_str(s: &str) -> ParseResult<NaiveTime>1477     fn from_str(s: &str) -> ParseResult<NaiveTime> {
1478         const HOUR_AND_MINUTE: &[Item<'static>] = &[
1479             Item::Numeric(Numeric::Hour, Pad::Zero),
1480             Item::Space(""),
1481             Item::Literal(":"),
1482             Item::Numeric(Numeric::Minute, Pad::Zero),
1483         ];
1484         const SECOND_AND_NANOS: &[Item<'static>] = &[
1485             Item::Space(""),
1486             Item::Literal(":"),
1487             Item::Numeric(Numeric::Second, Pad::Zero),
1488             Item::Fixed(Fixed::Nanosecond),
1489             Item::Space(""),
1490         ];
1491         const TRAILING_WHITESPACE: [Item<'static>; 1] = [Item::Space("")];
1492 
1493         let mut parsed = Parsed::new();
1494         let s = parse_and_remainder(&mut parsed, s, HOUR_AND_MINUTE.iter())?;
1495         // Seconds are optional, don't fail if parsing them doesn't succeed.
1496         let s = parse_and_remainder(&mut parsed, s, SECOND_AND_NANOS.iter()).unwrap_or(s);
1497         parse(&mut parsed, s, TRAILING_WHITESPACE.iter())?;
1498         parsed.to_naive_time()
1499     }
1500 }
1501 
1502 /// The default value for a NaiveTime is midnight, 00:00:00 exactly.
1503 ///
1504 /// # Example
1505 ///
1506 /// ```rust
1507 /// use chrono::NaiveTime;
1508 ///
1509 /// let default_time = NaiveTime::default();
1510 /// assert_eq!(default_time, NaiveTime::from_hms_opt(0, 0, 0).unwrap());
1511 /// ```
1512 impl Default for NaiveTime {
default() -> Self1513     fn default() -> Self {
1514         NaiveTime::from_hms_opt(0, 0, 0).unwrap()
1515     }
1516 }
1517 
1518 #[cfg(all(test, any(feature = "rustc-serialize", feature = "serde")))]
test_encodable_json<F, E>(to_string: F) where F: Fn(&NaiveTime) -> Result<String, E>, E: ::std::fmt::Debug,1519 fn test_encodable_json<F, E>(to_string: F)
1520 where
1521     F: Fn(&NaiveTime) -> Result<String, E>,
1522     E: ::std::fmt::Debug,
1523 {
1524     assert_eq!(
1525         to_string(&NaiveTime::from_hms_opt(0, 0, 0).unwrap()).ok(),
1526         Some(r#""00:00:00""#.into())
1527     );
1528     assert_eq!(
1529         to_string(&NaiveTime::from_hms_milli_opt(0, 0, 0, 950).unwrap()).ok(),
1530         Some(r#""00:00:00.950""#.into())
1531     );
1532     assert_eq!(
1533         to_string(&NaiveTime::from_hms_milli_opt(0, 0, 59, 1_000).unwrap()).ok(),
1534         Some(r#""00:00:60""#.into())
1535     );
1536     assert_eq!(
1537         to_string(&NaiveTime::from_hms_opt(0, 1, 2).unwrap()).ok(),
1538         Some(r#""00:01:02""#.into())
1539     );
1540     assert_eq!(
1541         to_string(&NaiveTime::from_hms_nano_opt(3, 5, 7, 98765432).unwrap()).ok(),
1542         Some(r#""03:05:07.098765432""#.into())
1543     );
1544     assert_eq!(
1545         to_string(&NaiveTime::from_hms_opt(7, 8, 9).unwrap()).ok(),
1546         Some(r#""07:08:09""#.into())
1547     );
1548     assert_eq!(
1549         to_string(&NaiveTime::from_hms_micro_opt(12, 34, 56, 789).unwrap()).ok(),
1550         Some(r#""12:34:56.000789""#.into())
1551     );
1552     assert_eq!(
1553         to_string(&NaiveTime::from_hms_nano_opt(23, 59, 59, 1_999_999_999).unwrap()).ok(),
1554         Some(r#""23:59:60.999999999""#.into())
1555     );
1556 }
1557 
1558 #[cfg(all(test, any(feature = "rustc-serialize", feature = "serde")))]
test_decodable_json<F, E>(from_str: F) where F: Fn(&str) -> Result<NaiveTime, E>, E: ::std::fmt::Debug,1559 fn test_decodable_json<F, E>(from_str: F)
1560 where
1561     F: Fn(&str) -> Result<NaiveTime, E>,
1562     E: ::std::fmt::Debug,
1563 {
1564     assert_eq!(from_str(r#""00:00:00""#).ok(), Some(NaiveTime::from_hms_opt(0, 0, 0).unwrap()));
1565     assert_eq!(from_str(r#""0:0:0""#).ok(), Some(NaiveTime::from_hms_opt(0, 0, 0).unwrap()));
1566     assert_eq!(
1567         from_str(r#""00:00:00.950""#).ok(),
1568         Some(NaiveTime::from_hms_milli_opt(0, 0, 0, 950).unwrap())
1569     );
1570     assert_eq!(
1571         from_str(r#""0:0:0.95""#).ok(),
1572         Some(NaiveTime::from_hms_milli_opt(0, 0, 0, 950).unwrap())
1573     );
1574     assert_eq!(
1575         from_str(r#""00:00:60""#).ok(),
1576         Some(NaiveTime::from_hms_milli_opt(0, 0, 59, 1_000).unwrap())
1577     );
1578     assert_eq!(from_str(r#""00:01:02""#).ok(), Some(NaiveTime::from_hms_opt(0, 1, 2).unwrap()));
1579     assert_eq!(
1580         from_str(r#""03:05:07.098765432""#).ok(),
1581         Some(NaiveTime::from_hms_nano_opt(3, 5, 7, 98765432).unwrap())
1582     );
1583     assert_eq!(from_str(r#""07:08:09""#).ok(), Some(NaiveTime::from_hms_opt(7, 8, 9).unwrap()));
1584     assert_eq!(
1585         from_str(r#""12:34:56.000789""#).ok(),
1586         Some(NaiveTime::from_hms_micro_opt(12, 34, 56, 789).unwrap())
1587     );
1588     assert_eq!(
1589         from_str(r#""23:59:60.999999999""#).ok(),
1590         Some(NaiveTime::from_hms_nano_opt(23, 59, 59, 1_999_999_999).unwrap())
1591     );
1592     assert_eq!(
1593         from_str(r#""23:59:60.9999999999997""#).ok(), // excess digits are ignored
1594         Some(NaiveTime::from_hms_nano_opt(23, 59, 59, 1_999_999_999).unwrap())
1595     );
1596 
1597     // bad formats
1598     assert!(from_str(r#""""#).is_err());
1599     assert!(from_str(r#""000000""#).is_err());
1600     assert!(from_str(r#""00:00:61""#).is_err());
1601     assert!(from_str(r#""00:60:00""#).is_err());
1602     assert!(from_str(r#""24:00:00""#).is_err());
1603     assert!(from_str(r#""23:59:59,1""#).is_err());
1604     assert!(from_str(r#""012:34:56""#).is_err());
1605     assert!(from_str(r#""hh:mm:ss""#).is_err());
1606     assert!(from_str(r#"0"#).is_err());
1607     assert!(from_str(r#"86399"#).is_err());
1608     assert!(from_str(r#"{}"#).is_err());
1609     // pre-0.3.0 rustc-serialize format is now invalid
1610     assert!(from_str(r#"{"secs":0,"frac":0}"#).is_err());
1611     assert!(from_str(r#"null"#).is_err());
1612 }
1613