Home > Blockchain >  Setting weekday of a date returns a wrong result that is next week
Setting weekday of a date returns a wrong result that is next week

Time:01-11

I am trying to wrap my head around why setting the weekday property of a date would set the wrong date for Monday. Calling the following:

print(Date().description(with: .current))
print("--")
print(Calendar.current.date(bySetting: .weekday, value: 2, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 3, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 4, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 5, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 6, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 7, of: Date())?.description(with: .current))
print(Calendar.current.date(bySetting: .weekday, value: 1, of: Date())?.description(with: .current))

Prints this:

Tuesday, 3 January 2023 at 02:07:35 Eastern European Standard Time
--
Monday, 9 January 2023 at 00:00:00 Eastern European Standard Time
Tuesday, 3 January 2023 at 02:07:35 Eastern European Standard Time
Wednesday, 4 January 2023 at 00:00:00 Eastern European Standard Time
Thursday, 5 January 2023 at 00:00:00 Eastern European Standard Time
Friday, 6 January 2023 at 00:00:00 Eastern European Standard Time
Saturday, 7 January 2023 at 00:00:00 Eastern European Standard Time
Sunday, 8 January 2023 at 00:00:00 Eastern European Standard Time

Why is setting the weekday to 2 returning Monday the 9th, which is next week, as opposed to the expected result, which is Monday the 2nd?

If I try to set the weekOfYear property to date, all the others still work fine, but Monday is now in 2024.

CodePudding user response:

This is the expected behavior. The function will try to produce a result which is in the next-larger component to the one given. So in this case it won't give 2 as you expect. It would return 9.

For more clarification read the document here.

Changing a component’s value often will require higher or coupled components to change as well. For example, setting the Weekday to Thursday usually will require the Day component to change its value, and possibly the Month and Year as well. If no such time exists, the next available time is returned (which could, for example, be in a different day, week, month, … than the nominal target date). Setting a component to something which would be inconsistent forces other components to change; for example, setting the Weekday to Thursday probably shifts the Day and possibly Month and Year. The exact behavior of this method is implementation-defined. For example, if changing the weekday to Thursday, does that move forward to the next, backward to the previous, or to the nearest Thursday? The algorithm will try to produce a result which is in the next-larger component to the one given (there’s a table of this mapping at the top of this document). So for the “set to Thursday” example, find the Thursday in the Week in which the given date resides (which could be a forwards or backwards move, and not necessarily the nearest Thursday). For more control over the exact behavior, use nextDate(after:matching:matchingPolicy:behavior:direction:).

  • Related