Skip to content

Commit

Permalink
use TimeInterval instead of Duration for calculating ISO week date (#…
Browse files Browse the repository at this point in the history
…22091)

* use TimeInterval instead of Duration for calculating ISO week date

hopefully actually fixes (space) #22059

* forward declare

* explicit effects
  • Loading branch information
metagn committed Jun 14, 2023
1 parent 44f377e commit 13b7e4e
Showing 1 changed file with 30 additions and 17 deletions.
47 changes: 30 additions & 17 deletions lib/pure/times.nim
Original file line number Diff line number Diff line change
Expand Up @@ -1523,31 +1523,17 @@ proc getClockStr*(dt = now()): string {.rtl, extern: "nt$1", tags: [TimeEffect].


#
# Iso week
# Iso week forward declarations
#

proc initDateTime*(weekday: WeekDay, isoweek: IsoWeekRange, isoyear: IsoYear,
hour: HourRange, minute: MinuteRange, second: SecondRange,
nanosecond: NanosecondRange,
zone: Timezone = local()): DateTime {.since: (1, 5).} =
## Create a new `DateTime <#DateTime>`_ from a weekday and an ISO 8601 week number and year
## in the specified timezone.
##
## .. warning:: The ISO week-based year can correspond to the following or previous year from 29 December to January 3.
runnableExamples:
assert initDateTime(21, mApr, 2018, 00, 00, 00) == initDateTime(dSat, 16, 2018.IsoYear, 00, 00, 00)
assert initDateTime(30, mDec, 2019, 00, 00, 00) == initDateTime(dMon, 01, 2020.IsoYear, 00, 00, 00)
assert initDateTime(13, mSep, 2020, 00, 00, 00) == initDateTime(dSun, 37, 2020.IsoYear, 00, 00, 00)
assert initDateTime(2, mJan, 2021, 00, 00, 00) == initDateTime(dSat, 53, 2020.IsoYear, 00, 00, 00)

# source https://webspace.science.uu.nl/~gent0113/calendar/isocalendar.htm
let d = isoweek * 7 + weekday.int - initDateTime(4, mJan, isoyear.int, 00, 00, 00, zone).weekday.int - 4
initDateTime(1, mJan, isoyear.int, hour, minute, second, nanosecond, zone) + initDuration(days=d)
zone: Timezone = local()): DateTime {.raises: [], tags: [], since: (1, 5).}

proc initDateTime*(weekday: WeekDay, isoweek: IsoWeekRange, isoyear: IsoYear,
hour: HourRange, minute: MinuteRange, second: SecondRange,
zone: Timezone = local()): DateTime {.since: (1, 5).} =
initDateTime(weekday, isoweek, isoyear, hour, minute, second, 0, zone)
zone: Timezone = local()): DateTime {.raises: [], tags: [], since: (1, 5).}

#
# TimeFormat
Expand Down Expand Up @@ -2761,6 +2747,33 @@ proc `+=`*(t: var Time, b: TimeInterval) =
proc `-=`*(t: var Time, b: TimeInterval) =
t = t - b

#
# Iso week
#

proc initDateTime*(weekday: WeekDay, isoweek: IsoWeekRange, isoyear: IsoYear,
hour: HourRange, minute: MinuteRange, second: SecondRange,
nanosecond: NanosecondRange,
zone: Timezone = local()): DateTime {.raises: [], tags: [], since: (1, 5).} =
## Create a new `DateTime <#DateTime>`_ from a weekday and an ISO 8601 week number and year
## in the specified timezone.
##
## .. warning:: The ISO week-based year can correspond to the following or previous year from 29 December to January 3.
runnableExamples:
assert initDateTime(21, mApr, 2018, 00, 00, 00) == initDateTime(dSat, 16, 2018.IsoYear, 00, 00, 00)
assert initDateTime(30, mDec, 2019, 00, 00, 00) == initDateTime(dMon, 01, 2020.IsoYear, 00, 00, 00)
assert initDateTime(13, mSep, 2020, 00, 00, 00) == initDateTime(dSun, 37, 2020.IsoYear, 00, 00, 00)
assert initDateTime(2, mJan, 2021, 00, 00, 00) == initDateTime(dSat, 53, 2020.IsoYear, 00, 00, 00)

# source https://webspace.science.uu.nl/~gent0113/calendar/isocalendar.htm
let d = isoweek * 7 + weekday.int - initDateTime(4, mJan, isoyear.int, 00, 00, 00, zone).weekday.int - 4
initDateTime(1, mJan, isoyear.int, hour, minute, second, nanosecond, zone) + initTimeInterval(days=d)

proc initDateTime*(weekday: WeekDay, isoweek: IsoWeekRange, isoyear: IsoYear,
hour: HourRange, minute: MinuteRange, second: SecondRange,
zone: Timezone = local()): DateTime {.raises: [], tags: [], since: (1, 5).} =
initDateTime(weekday, isoweek, isoyear, hour, minute, second, 0, zone)

#
# Other
#
Expand Down

0 comments on commit 13b7e4e

Please sign in to comment.