swift - 日期格式化程序 swift 崩溃

标签 swift nsdateformatter date-formatting

请帮我修改这部分代码,

if let dateVaule = UserDefaults().value(forKey: SplashSeenDate){
            let dateStr  = dateVaule as! String
            let dateFormatter = DateFormatter()
            dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
            dateFormatter.timeZone = TimeZone.ReferenceType.local
            let date = dateFormatter.date(from:dateStr)
            if Global.sharedInstance.Splashs != nil && Global.sharedInstance.Splashs?.count != 0{

                for (i,splash) in (Global.sharedInstance.Splashs?.enumerated().reversed())!{
                    if !checkTimeStamp(date: splash.create_timestamp,StoredDate: date!){
                        Global.sharedInstance.Splashs?.remove(at: i)
                    }
                }
                print(Global.sharedInstance.Splashs?.count ?? "-1")
            }
        }

老实说,我对日期格式化程序很困惑。 当这个项目启动时,它发生了崩溃

if !checkTimeStamp(date: splash.create_timestamp,StoredDate: date!){

但是,我无法重现此崩溃... **只有少数 iOS10 用户发生此崩溃。**请指教,非常感谢!

func checkTimeStamp(date: String!,StoredDate: Date) -> Bool {
    let dateFormatter: DateFormatter = DateFormatter()
    dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
    dateFormatter.locale = Locale(identifier:"en_US_POSIX")
    let datecomponents = dateFormatter.date(from: date)

    if (datecomponents! >= StoredDate) {
        return true
    } else {
        return false
    }
}

最佳答案

您正在以两种不同的方式将 String 转换为 Date:

let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
dateFormatter.timeZone = TimeZone.ReferenceType.local //###Why don't you use `TimeZone.current`?
let date = dateFormatter.date(from:dateStr)

并且在 checkTimeStamp(date: String!,StoredDate: Date) -> Bool 中:

let dateFormatter: DateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
dateFormatter.locale = Locale(identifier:"en_US_POSIX")
let datecomponents = dateFormatter.date(from: date)

在您的情况下,缺少此行对于您的首次转化至关重要:

dateFormatter.locale = Locale(identifier: "en_US_POSIX")

您可以找到许多讨论返回 nilDateFormatter(或旧文章中的 NSDateFormatter)的文章。

当你使用 DateFormatter 的固定格式如 "yyyy-MM-dd HH:mm:ss" 时,你必须将 locale 设置为区域设置(标识符:“en_US_POSIX”)

也许您最好定义一种转换方法(或计算属性)以将 String 转换为适合您应用要求的 Date,并在您需要的任何地方使用它 StringDate 的转换:

extension String {
    var toAppDate: Date? {
        let dateFormatter = DateFormatter()
        dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
        dateFormatter.timeZone = TimeZone.current
        dateFormatter.locale = Locale(identifier: "en_US_POSIX") //### <- Do not miss.
        return dateFormatter.date(from: self)
    }
}

通常,您的代码使用了过多的强制解包或强制转换。您可以在不使用任何强制的情况下重写它:

    if
        let dateStr = UserDefaults().string(forKey: SplashSeenDate),
        let date = dateStr.toAppDate,
        let splashes = Global.sharedInstance.Splashs, !splashes.isEmpty
    {
        //### In most cases, `filter` is faster than repeated `remove`.
        Global.sharedInstance.Splashs = splashes.filter {
            checkTimeStamp(date: $0.create_timestamp, storedDate: date)
        }
        print(Global.sharedInstance.Splashs?.count ?? "-1")
    }

(假设 create_timestamp 不是可选的,并将参数标签 StoredDate: 重命名为 storedDate:。)

关于swift - 日期格式化程序 swift 崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45406393/

相关文章:

xcode - 工具栏中的间隙,Xcode

ios - 纠正 UINavigationController 方向

php - 使 PHP/MySQL 时间戳看起来更有吸引力

java - LocalDate Formatter 月份基数

java - 使用 SimpleDateFormat.parse() 时获取错误数据

ios - 如何从模拟器(IOS)获取Iphone类型

swift - 为什么列表中带有导航链接的项目变成蓝色?

ios - 在 sqlite 数据库中以 'GMT' 时区保存日期

ios - 将 MySQL 日期字段转换为字符串

ios - 将时间转换为 HH :mm:ss formate