Skip to main content

Date

Struct Date 

Source
pub struct Date { /* private fields */ }
Expand description

A Gregorian-calendar date — (year, month, day).

A Date is created by Date::ymd (validating) or Date::ymd_unchecked (caller asserts validity); the field layout is private so the invariant that the triple names a real date cannot be violated by direct construction. The type is Copy and allocates nothing.

PartialOrd / Ord follow the natural chronological order — equivalent to lexicographic order on (year, month, day), which is the same thing for Gregorian dates.

The accepted year range is 1583..=9999: the Gregorian calendar took effect in October 1582, and from 1583 onward every day-count and holiday-calendar rule this crate implements is defined uniformly.

§Examples

use regit_daycount::Date;

let d = Date::ymd(2026, 5, 23).unwrap();
assert_eq!(d.year(),  2026);
assert_eq!(d.month(), 5);
assert_eq!(d.day(),   23);

Implementations§

Source§

impl Date

Source

pub const MIN_YEAR: i32 = 1583

Smallest accepted year (1583 — the first full year after the Gregorian reform of October 1582).

Source

pub const MAX_YEAR: i32 = 9999

Largest accepted year (9999 — keeps the year an i16-fittable value and matches every published holiday-calendar horizon).

Source

pub fn ymd(year: i32, month: u8, day: u8) -> Result<Self, ValidationError>

Constructs a validated Date from a (year, month, day) triple.

Validation, in order: the year is in MIN_YEAR..=MAX_YEAR, the month is in 1..=12, and the day is in 1..=days_in_month(year, month) — which accounts for leap years.

§Errors
§Examples
use regit_daycount::{Date, ValidationError};

// A valid date.
assert!(Date::ymd(2026, 5, 23).is_ok());

// 2025 is not a leap year — 29 February is rejected.
assert_eq!(
    Date::ymd(2025, 2, 29),
    Err(ValidationError::InvalidDate { rule: "day-out-of-range" }),
);
Source

pub const fn ymd_unchecked(year: i32, month: u8, day: u8) -> Self

Constructs a Date without validating the triple.

The caller asserts that (year, month, day) names a real Gregorian date inside the supported year range. This exists for const-context construction and for reconstructing a Date from fields validated earlier; prefer Date::ymd for any untrusted input.

§Examples
use regit_daycount::Date;

let d = Date::ymd_unchecked(2026, 5, 23);
assert_eq!(d.year(), 2026);
Source

pub const fn year(&self) -> i32

Returns the year.

§Examples
use regit_daycount::Date;

assert_eq!(Date::ymd_unchecked(2026, 5, 23).year(), 2026);
Source

pub const fn month(&self) -> u8

Returns the month, 1..=12.

§Examples
use regit_daycount::Date;

assert_eq!(Date::ymd_unchecked(2026, 5, 23).month(), 5);
Source

pub const fn day(&self) -> u8

Returns the day of the month, 1..=31.

§Examples
use regit_daycount::Date;

assert_eq!(Date::ymd_unchecked(2026, 5, 23).day(), 23);
Source

pub const fn is_leap_year(year: i32) -> bool

Returns true if year is a Gregorian leap year.

A year is a leap year if it is divisible by 4 and either not divisible by 100 or divisible by 400. Hence 1900 is not a leap year, 2000 is, and 2100 is not.

§Examples
use regit_daycount::Date;

assert!( Date::is_leap_year(2000));
assert!( Date::is_leap_year(2024));
assert!(!Date::is_leap_year(1900));
assert!(!Date::is_leap_year(2025));
Source

pub const fn days_in_month(year: i32, month: u8) -> u8

Returns the number of days in (year, month).

February takes 29 days in a leap year and 28 otherwise; every other month is the conventional 30 or 31. If month is not in 1..=12, returns 0 (the caller is expected to validate the month first; Date::ymd does).

§Examples
use regit_daycount::Date;

assert_eq!(Date::days_in_month(2024, 2), 29);
assert_eq!(Date::days_in_month(2025, 2), 28);
assert_eq!(Date::days_in_month(2026, 4), 30);
assert_eq!(Date::days_in_month(2026, 7), 31);
Source

pub fn day_of_week(self) -> Weekday

Returns the day of the week for self.

Computed by reducing the Hinnant civil-day count modulo 7 (the civil epoch 1970-01-01 was a Thursday).

§Examples
use regit_daycount::{Date, Weekday};

assert_eq!(Date::ymd(2026, 5, 23).unwrap().day_of_week(), Weekday::Sat);
assert_eq!(Date::ymd(2000, 1,  1).unwrap().day_of_week(), Weekday::Sat);
assert_eq!(Date::ymd(2024, 12, 25).unwrap().day_of_week(), Weekday::Wed);
Source

pub fn add_days(self, days: i32) -> Self

Returns self advanced by days calendar days (negative goes back).

Implemented by converting self to its Hinnant civil-day count, adding days, and converting back. The intermediate arithmetic is i64, so a 32-bit days cannot overflow. The result is constructed via Self::ymd_unchecked and is not re-validated against the [1583, 9999] window — arithmetic that escapes that window is the caller’s responsibility.

§Examples
use regit_daycount::Date;

// Plain forward step into the next month.
assert_eq!(
    Date::ymd(2026, 1, 1).unwrap().add_days(31),
    Date::ymd(2026, 2, 1).unwrap(),
);

// Leap-year boundary.
assert_eq!(
    Date::ymd(2024, 2, 28).unwrap().add_days(1),
    Date::ymd(2024, 2, 29).unwrap(),
);
Source

pub fn add_months_eom_aware(self, months: i32) -> Self

Returns self advanced by months months, clamping the day of the month to the last day of the resulting month when the original day does not exist there.

The rule is: compute the new year and month from (self.year * 12 + self.month - 1) + months, then set the day to min(self.day, days_in_month(new_year, new_month)). So 2026-01-31 + 1 month = 2026-02-28 (not a leap year) and 2024-01-31 + 1 month = 2024-02-29 (leap year).

The result is constructed via Self::ymd_unchecked and is not re-validated against the [1583, 9999] window.

§Examples
use regit_daycount::Date;

assert_eq!(
    Date::ymd(2026, 1, 31).unwrap().add_months_eom_aware(1),
    Date::ymd(2026, 2, 28).unwrap(),
);
assert_eq!(
    Date::ymd(2024, 1, 31).unwrap().add_months_eom_aware(1),
    Date::ymd(2024, 2, 29).unwrap(),
);
Source

pub fn nth_weekday_of_month( year: i32, month: u8, n: u8, weekday: Weekday, ) -> Result<Self, ValidationError>

Returns the date of the n-th occurrence of weekday in (year, month).

n = 1 is the first occurrence, n = 5 is the fifth (if it exists). Computed by finding the first occurrence of weekday in the month and adding (n - 1) * 7 days.

§Errors
§Examples
use regit_daycount::{Date, Weekday};

// The 3rd Friday of June 2026 is 2026-06-19.
assert_eq!(
    Date::nth_weekday_of_month(2026, 6, 3, Weekday::Fri).unwrap(),
    Date::ymd(2026, 6, 19).unwrap(),
);
Source

pub fn easter_sunday(year: i32) -> Self

Returns the date of Easter Sunday in the (Western, Gregorian) year year.

Implemented by the Anonymous Gregorian / Computus algorithm (Meeus / Butcher form): a closed-form integer-only computation that is exact for every Gregorian year. See Jean Meeus, Astronomical Algorithms (2nd ed., 1998), §8 — “The date of Easter”.

The TARGET2 holiday rule derives Good Friday and Easter Monday from this date.

§Examples
use regit_daycount::Date;

// Easter Sunday 2026 falls on 5 April.
assert_eq!(Date::easter_sunday(2026), Date::ymd(2026, 4, 5).unwrap());
Source

pub fn days_between(self, other: Self) -> i32

Returns the signed number of days from self to other.

The convention is end-exclusive, start-inclusive: a one-day interval [2026-01-01, 2026-01-02) returns 1. Computed by subtracting the two Hinnant civil-day counts; the result is i32 and fits comfortably for any pair of dates in the supported year range (the full window 1583–9999 spans roughly 3.1 * 10⁶ days, well inside i32).

§Examples
use regit_daycount::Date;

let a = Date::ymd(2026, 1, 1).unwrap();
let b = Date::ymd(2026, 1, 2).unwrap();
assert_eq!(a.days_between(b),  1);
assert_eq!(b.days_between(a), -1);
assert_eq!(a.days_between(a),  0);

Trait Implementations§

Source§

impl Clone for Date

Source§

fn clone(&self) -> Date

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Copy for Date

Source§

impl Debug for Date

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl Eq for Date

Source§

impl Hash for Date

Source§

fn hash<__H: Hasher>(&self, state: &mut __H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl Ord for Date

Source§

fn cmp(&self, other: &Date) -> Ordering

This method returns an Ordering between self and other. Read more
1.21.0 (const: unstable) · Source§

fn max(self, other: Self) -> Self
where Self: Sized,

Compares and returns the maximum of two values. Read more
1.21.0 (const: unstable) · Source§

fn min(self, other: Self) -> Self
where Self: Sized,

Compares and returns the minimum of two values. Read more
1.50.0 (const: unstable) · Source§

fn clamp(self, min: Self, max: Self) -> Self
where Self: Sized,

Restrict a value to a certain interval. Read more
Source§

impl PartialEq for Date

Source§

fn eq(&self, other: &Date) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl PartialOrd for Date

Source§

fn partial_cmp(&self, other: &Date) -> Option<Ordering>

This method returns an ordering between self and other values if one exists. Read more
1.0.0 (const: unstable) · Source§

fn lt(&self, other: &Rhs) -> bool

Tests less than (for self and other) and is used by the < operator. Read more
1.0.0 (const: unstable) · Source§

fn le(&self, other: &Rhs) -> bool

Tests less than or equal to (for self and other) and is used by the <= operator. Read more
1.0.0 (const: unstable) · Source§

fn gt(&self, other: &Rhs) -> bool

Tests greater than (for self and other) and is used by the > operator. Read more
1.0.0 (const: unstable) · Source§

fn ge(&self, other: &Rhs) -> bool

Tests greater than or equal to (for self and other) and is used by the >= operator. Read more
Source§

impl StructuralPartialEq for Date

Auto Trait Implementations§

§

impl Freeze for Date

§

impl RefUnwindSafe for Date

§

impl Send for Date

§

impl Sync for Date

§

impl Unpin for Date

§

impl UnsafeUnpin for Date

§

impl UnwindSafe for Date

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.