如果我运行以下代码:
let date = Date()
let midnight = Calendar.current.date(bySetting: .hour, value: 0, of: date)!
let difference = Int64(midnight.timeIntervalSince(date))
print(String(difference))
差异是大约13个小时的正值(因为当地时间大约是上午11点)。但是,我预计差异将是负11小时;因为我将.hour
值设置为0
我希望时间会向后移动,而不是向前移动。
我希望明天能用这段代码找到午夜:
let midnight = Calendar.current.date(bySetting: .hour, value: 0, of:
Calendar.current.date(byAdding: .day, value: 1, to: date)!)!
但是这给了+37小时而不是+13。
目前的行为实际上是我想要的行为(我想知道明天午夜之前的时间)。但是,我想了解为什么会发生这种情况,特别是我想确保明天午夜的这种方法无论时区如何都能奏效。谢谢!
编辑:注意,我只关心午夜的时间,这就是为什么我在找到午夜时不会改变分钟或秒值。
答案 0 :(得分:5)
我认为这是预期的,正如它在documentation中所说的那样,
该算法将尝试生成下一个更大的结果 组件到给定的组件(顶部有一个映射表) 这份文件)。因此,对于“设置为星期四”的例子,找到 星期四在给定日期所在的周(可能是一个 向前或向后移动,而不一定是最近的星期四)。 要更好地控制确切的行为,请使用 nextDate(后:匹配:matchingPolicy:行为:方向:)
。
使用nextDate(after date: Date, matching components: DateComponents, matchingPolicy: Calendar.MatchingPolicy, repeatedTimePolicy: Calendar.RepeatedTimePolicy = default, direction: Calendar.SearchDirection = default) -> Date?
会产生正确的结果,如您所料。
示例在这里,
let calendar = Calendar.current
var hourComponent = DateComponents()
hourComponent.hour = 0
let midnightSameDay = calendar.nextDate(after: date,
matching: hourComponent,
matchingPolicy: .nextTime,
direction: .backward)
print(mightnightSameDay) // 2018-04-19 00:00:00 +0000
let midnightNextDay = calendar.nextDate(after: date,
matching: hourComponent,
matchingPolicy: .nextTime,
direction: .forward)
print(mightnightNextDay) // 2018-04-20 00:00:00 +0000
还有另一种可以用于此的方法,它使用搜索方向和匹配策略,
let midnightSameDay = calendar.date(bySettingHour: 0,
minute: 0,
second: 0,
of: date,
direction: .backward)
答案 1 :(得分:1)
date(bySetting:value:of)
做出最佳猜测,即#34;实施定义"根据新参数创建新的Date
。通过将hour
设置为0
- 有时这会在相同的日历日创建Date
,并相应地设置hour
,有时新的Date
会明天。听起来并不能说明你需要的可靠性,但希望它可以回答你的问题。
文档更深入:
https://developer.apple.com/documentation/foundation/calendar/2292915-date