Swift Date功能未按预期工作
我试图用Swift 4.1找出两个日期在几秒钟内的差异。这是我使用的代码Swift Date功能未按预期工作,swift,swiftdate,Swift,Swiftdate,我试图用Swift 4.1找出两个日期在几秒钟内的差异。这是我使用的代码 func getDurationInSeconds(date1 :Date) -> Int{ guard let durationInSeconds = Calendar.current.dateComponents([.second], from: Date(), to: date1).second else { return 0 } return durationI
func getDurationInSeconds(date1 :Date) -> Int{
guard let durationInSeconds = Calendar.current.dateComponents([.second], from: Date(), to: date1).second else {
return 0
}
return durationInSeconds
}
函数从2018-10-09T18:19:00Z生成日期1
func dateFromString(stringDate:String) -> Date? {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
dateFormatter.locale = NSLocale(localeIdentifier: "en_US_POSIX") as Locale?
let date = dateFormatter.date(from: stringDate)
return date
}
日期返回的时间总是比我当前的设备时间少一个小时,因此计算无法按预期进行。如果我当前的设备时间是16:34,则Date()函数将其返回为15:34
我已经看到Date()返回的是UTC时间,而不是基于我的时区
此时,如果我传入日期2018年10月9日14:25:00,当前设备时间为2018年10月9日14:20:00。我希望此函数返回一个值300,即两个日期之间相差60*5分钟
但是我得到一个值3900,这是因为date函数将日期返回为
2018年10月9日13:20:00而不是14:20
。因此,持续时间为1小时+300秒的差值
包括Xcode控制台的示例输出,我执行此代码时的设备时间是2018-10-09 17:56:28.565423
(lldb) po date1
▿ 2018-10-09 17:59:00 +0000
- timeIntervalSinceReferenceDate : 560800740.0
(lldb) po durationInSeconds
3731
(lldb) po Date()
▿ 2018-10-09 16:57:04 +0000
- timeIntervalSinceReferenceDate : 560797024.35021996
(lldb)
但是,我找不到一个合适的方法,根据我当前的时区,找到两次之间正确的持续时间。如何操作?由于您使用的字符串表示时区中的当前时间,请尝试以下操作:
func getDurationInSeconds(date1: Date) -> Int {
return Int(-date1.timeIntervalSinceNow + TimeZone.current.daylightSavingTimeOffset(for: date1))
}
它使用属性和方法
或者如果您想在dateFromString(stringDate:)
中说明时区与UTC的差异:
测试
我在UTC+1h时区:
let str = "2018-10-09T19:50:00Z" //"2018-10-09T19:50:00Z"
let date1 = dateFromString(stringDate: str)! //"Oct 9, 2018 at 7:50 PM"
Date() //At the time of testing this it is "Oct 9, 2018 at 7:53 PM"
getDurationInSeconds(date1: date1) //213, which is 3 minutes and 33 seconds
问题不在于Date()返回了错误的时间。Date()始终返回当前时间,该时间实际上并不基于(任何其他)本地时区
问题似乎出在用于从日期字符串生成日期对象的日期格式化程序上
请尝试使用以下代码行:
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss"
// Not necessary as the dateFormatter would take the device's timeZone to be the default.
dateFormatter.timeZone = Calendar.current.timeZone
而不是:
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
后者的问题是,您将“Z”指定为零偏移时区(UTC)。因此,设备中与UTC相差1小时会导致此偏移
并且,在传递日期字符串时,请确保跳过末尾的“Z”(例如,它应该类似于2018-10-09T18:19:00)
更新后的代码应该对您有好处,并以秒为单位返回预期的差异。
Date()与Date
相同pointless@rmaddydate one没有问题,date()的值关闭了一个小时。请查看我的控制台输出。date1现在是硬编码的,很好。我只对Swift的Date()功能的输出有问题。@EasyCoder您要查找的是返回日期1.timeIntervalSinceNow
注意,如果您想要整数返回整数(date1.timeIntervalSinceNow)
请阅读:“一个特定时间点的表示,与任何日历或时区无关。”(强调部分加上。)“以我的时区为日期的正确时间”的概念没有意义,因为日期
与时区无关。只有在日期
与字符串之间转换时,或者在日期
与日期组件
之间转换时,时区才有意义,执行这些转换的对象允许您指定时区。@EasyCoder请阅读以了解更多信息。@EasyCoderr了解日期。这与OP的实际问题无关。这只是另一种编写代码的方法,它已经可以正常工作。这是错误的。不需要调整日光节约时间。OP的getDurationInSeconds函数没有任何错误。它以什么方式错了?你能详细说明一下吗?OP想要获得dur表示当前时区中的时间的字符串与“现在”之间的差异。获取两个Date
实例之间的差异不涉及任何时区。Date
没有时区。加入日光节约时间没有任何意义。到目前为止,问题中发布的任何代码都没有问题。您的试图“修复”此特定函数不需要,因为它不是问题所在。@rmaddy如果我正确理解操作,则他们传递的字符串应该在其时区内,而不是默认UTC。在dateFromString
中设置时区对输出日期?
没有影响。可以通过在返回日期之前或在getDurationInSeconds
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"