【发布时间】:2017-10-27 00:45:37
【问题描述】:
我知道在 iOS/Swift 中创建 DateFormatters 和设置 .dateFormats 很昂贵,我在 SO 和博客中阅读了很多不同的观点,但我仍然不确定有效处理 DateFormatter 的最佳方法和.dateFormat。具体来说,我正在使用一个大致模仿苹果 iPhone 天气应用程序 UI 的应用程序。日期通过 API 以timeIntervalSince1970/Unix 格式到达。在每个视图控制器上,我将使用一个 .dateFormat 来表示当前天气,例如“EEEE, MMM dd, y”,另一个用于在每日天气表视图中的 7 个单元格中的每个单元格中格式化日期,例如“EEEE”,另一个在水平滚动的集合视图中以 24 个单元格显示一个小时,例如“哈”。用户还为他们保存的每个位置翻阅各种视图控制器。我没有注意到对性能有太大影响,但我真的很想确保我的效率最高,并正确地考虑到这一点(例如,单例是要走的路吗?)。
我创建了一个带有单个DateFormatter 作为静态变量的单例,还创建了一个函数来设置日期格式化程序的.dateFormat 和.timeZone(见下文)。根据之前的阅读,我假设如果我坚持使用 iOS 10 或更高版本,我不必担心线程安全性,而且在这类应用程序中这可能不是问题。
class Formatter {
static var dateFormatter = DateFormatter()
private init() {}
static func formatTimeForTimeZone(unixDate: TimeInterval, formatString: String, timeZone: String) -> String {
let usableDate = Date(timeIntervalSince1970: unixDate)
self.dateFormatter.dateFormat = formatString
self.dateFormatter.timeZone = TimeZone(identifier: timeZone)
let dateString = self.dateFormatter.string(from: usableDate)
return dateString
}
}
每次我需要在视图或自定义单元格类中设置日期时,我只需调用该函数,并传入适当的值,如下所示:
let dateString = Formatter.formatTimeForTimeZone(unixDate: someTime, formatString: someFormatString, timeZone: someTimeZone)
由于我在每次调用(在每个单元格中)设置一个 .formatString ,这种方法并没有为我节省太多,这是否正确?如果是这样,是否有更合理的方法?非常感谢您让我直截了当。
【问题讨论】:
-
这对我来说似乎是过早的优化。除非您有数千/数万个日期要使用
DateFormatters 进行格式化,否则您不应该真正担心它的性能。特别是如果您在您的应用支持的最旧设备上测试您的代码并且没有发现任何性能问题,那么您的代码应该可以继续使用。 -
你不应该命名你的类格式化程序。 Swift 已经有一个类带格式化程序。只需使用扩展将您的静态方法或属性添加到它。 developer.apple.com/documentation/foundation/formatter
-
顺便说一句,无需使用
var将您的 dateFormatter 声明为变量。DateFormatter它是一个类,因此即使您使用let将其声明为常量,您也可以更改其属性。 -
关于你的问题。这不是单例。您甚至没有在任何地方实例化您的 Formatter 类。如果您想学习如何创建单例,您应该阅读采用 Cocoa 设计模式指南。 developer.apple.com/library/content/documentation/Swift/… 和这个答案 stackoverflow.com/questions/28016578/…
-
谢谢,Leo - 非常有帮助。我在下面发布了一个从 Sandmoose 的代码修改的替代 DateFormatter 缓存解决方案(希望这个礼仪是正确的),但我想知道设置缓存的 DateFormatter 的 .timeZone 或使用 .string(from: somePOSIXdate) 是否与设置 .dateFormat 或创建一样昂贵一个新的日期。如果是这样,那么我并没有真正获得希望的效率。感谢您的建议!
标签: ios swift dateformatter