Why does `ordinality(of: .day, in: .era, for: date)` give the same result for 2 dates in different time zones?

我与影子孤独终老i 提交于 2019-12-11 06:43:25

问题


Consider the following code:

import UIKit

let date = Date()

guard let nycTimeZone = TimeZone(abbreviation: "EST"),
  let nzTimeZone = TimeZone(abbreviation: "NZDT") else {
    fatalError()
}
var nycCalendar = Calendar(identifier: .gregorian)
nycCalendar.timeZone = nycTimeZone
var nzCalendar = Calendar(identifier: .gregorian)
nzCalendar.timeZone = nzTimeZone

let now = Date()

let nycDayOfEra = nycCalendar.ordinality(of: .day, in: .era, for: now)
let nycDayOfYear = nycCalendar.ordinality(of: .day, in: .year, for: now)

var nzDayOfEra = nzCalendar.ordinality(of: .day, in: .era, for: now)
var nzDayOfYear = nzCalendar.ordinality(of: .day, in: .year, for: now)

As I write this, NYC time and Aukland NZ time give different days. That's the case I'm interested in.

With the code above, the results for nycDayOfYear and nzDayOfYear are different (as of this writing I get nycDayOfYear=42 and nzDayOfYear=43.)

That is as expected, and as desired. (I was working to answer a "how do I calculate the number of days of difference in two Dates evaluated in different time zones?" question.)

However, it would take a bunch of messy adjustments to make the above day-of-year calculation and figure out the number of days of difference between those local dates when they span year boundaries.

I therefore tried to do the calculations using ordinality(of: .day, in: .era, for: date).

However, the calculations based on calendar era give the same value regardless of the time zone of the calendar used to make do the calculation.

Why is that?

What would be a simpler way to calculate the number of calendar days difference between two dates WHEN EXPRESSED IN DIFFERENT LOCAL TIME ZONES? Like I said, my code that calculates the day of year would need additional logic added to handle dates that span calendar year boundaries.

Note that this is a different question than "How many days difference is there between 2 dates". In my question I want both dates to be expressed in different local time zones, and I'm interested in the difference in the calendar date of each of those date values.


回答1:


Martin's comment about calendar calculations over long intervals giving unexpected results is as good an answer as any as to why it doesn't work.

I did come up with code that calculates the desired difference in calendar date values between 2 dates expressed in specific time zones:

let date = Date()

guard let nycTimeZone = TimeZone(abbreviation: "EST"),
  let nzTimeZone = TimeZone(abbreviation: "NZDT") else {
    fatalError()
}
var nycCalendar = Calendar(identifier: .gregorian)
nycCalendar.timeZone = nycTimeZone
var nzCalendar = Calendar(identifier: .gregorian)
nzCalendar.timeZone = nzTimeZone

let now = Date()


let nycDateComponents = nycCalendar.dateComponents([.month, .day, .year], from: now)
let nzDateComponents = nzCalendar.dateComponents([.month, .day, .year], from: now)

let difference = Calendar.current.dateComponents([.day],
  from: nycDateComponents,
    to: nzDateComponents)

let daysDifference = difference.days

First I convert the 2 dates to month/day/year DateComponents values using calendars set to their specific time zone.

Then I use the Calendar function dateComponents(_:from:to:), which lets you calculate the difference between 2 DateComponents values, in whatever units you want to use to compare them. (days, in this case)



来源:https://stackoverflow.com/questions/42178816/why-does-ordinalityof-day-in-era-for-date-give-the-same-result-for-2

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!