MCPcopy Create free account
hub / github.com/apache/arrow-rs / parse_date

Function parse_date

arrow-cast/src/parse.rs:614–692  ·  view source on GitHub ↗
(string: &str)

Source from the content-addressed store, hash-verified

612}
613
614fn parse_date(string: &str) -> Option<NaiveDate> {
615 // If the date has an extended (signed) year such as "+10999-12-31" or "-0012-05-06"
616 //
617 // According to [ISO 8601], years have:
618 // Four digits or more for the year. Years in the range 0000 to 9999 will be pre-padded by
619 // zero to ensure four digits. Years outside that range will have a prefixed positive or negative symbol.
620 //
621 // [ISO 8601]: https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/time/format/DateTimeFormatter.html#ISO_LOCAL_DATE
622 if string.starts_with('+') || string.starts_with('-') {
623 let (year, month, day) = parse_extended_ymd(string)?;
624 return NaiveDate::from_ymd_opt(year, month, day);
625 }
626
627 if string.len() > 10 {
628 // Try to parse as datetime and return just the date part
629 return string_to_datetime(&Utc, string)
630 .map(|dt| dt.date_naive())
631 .ok();
632 };
633 let mut digits = [0; 10];
634 let mut mask = 0;
635
636 // Treating all bytes the same way, helps LLVM vectorise this correctly
637 for (idx, (o, i)) in digits.iter_mut().zip(string.bytes()).enumerate() {
638 *o = i.wrapping_sub(b'0');
639 mask |= ((*o < 10) as u16) << idx
640 }
641
642 const HYPHEN: u8 = b'-'.wrapping_sub(b'0');
643
644 // refer to https://www.rfc-editor.org/rfc/rfc3339#section-3
645 if digits[4] != HYPHEN {
646 let (year, month, day) = match (mask, string.len()) {
647 (0b11111111, 8) => (
648 digits[0] as u16 * 1000
649 + digits[1] as u16 * 100
650 + digits[2] as u16 * 10
651 + digits[3] as u16,
652 digits[4] * 10 + digits[5],
653 digits[6] * 10 + digits[7],
654 ),
655 _ => return None,
656 };
657 return NaiveDate::from_ymd_opt(year as _, month as _, day as _);
658 }
659
660 let (month, day) = match mask {
661 0b1101101111 => {
662 if digits[7] != HYPHEN {
663 return None;
664 }
665 (digits[5] * 10 + digits[6], digits[8] * 10 + digits[9])
666 }
667 0b101101111 => {
668 if digits[7] != HYPHEN {
669 return None;
670 }
671 (digits[5] * 10 + digits[6], digits[8])

Callers 2

parse_date_to_daysFunction · 0.85
parseMethod · 0.85

Calls 6

parse_extended_ymdFunction · 0.85
string_to_datetimeFunction · 0.85
zipMethod · 0.80
lenMethod · 0.45
bytesMethod · 0.45
wrapping_subMethod · 0.45

Tested by

no test coverage detected