在 iPhone 上测试时应用程序崩溃,但在模拟器中没有

Posted

技术标签:

【中文标题】在 iPhone 上测试时应用程序崩溃,但在模拟器中没有【英文标题】:App crashes when tested on iPhone, but not in simulator 【发布时间】:2018-07-03 16:43:42 【问题描述】:

我有一个代码,它从 twitter 获取 JSON 并将其放入名为 feedStruct 的结构中,但还将其解析到 UITableViewController。

我已经在模拟器中测试了多次,但也想在我的 iPhone 上测试它,然后它在这段代码中崩溃了。我在“使应用程序崩溃”这一行旁边发表了评论:

线程 8:致命错误:在展开可选值时意外发现 nil

(我认为它在某些时候说线程 6 也想过,如果这与它有关的话。)

代码如下:

import Foundation

protocol twitterModelProtocol: class 
    func twitterDownloaded(items: [Any])
    func feedTwitterDatesDownloaded(items: [feedStruct])


class twitterModel: NSObject 

    //properties
    weak var delegate: twitterModelProtocol!

    let urlPath = "http://MYWEBPAGE/twit.php" //this will be changed to the path where service.php lives

    func downloadTwitterItems() 
        let url: URL = URL(string: urlPath)!
        let defaultSession = Foundation.URLSession(configuration: URLSessionConfiguration.default)
        let task = defaultSession.dataTask(with: url)  (data, response, error) in
            if error != nil 
                print("Failed to download twitter data")
             else 
                print("Twitter data downloaded")
                self.parseTwitterJSON(data!)
            
            
        task.resume()
    

    func parseTwitterJSON(_ data:Data) 
        var jsonResult = [Any]()

        do
            jsonResult = try JSONSerialization.jsonObject(with: data, options:JSONSerialization.ReadingOptions.allowFragments) as! [Any]
         catch let error as NSError 
            print(error)
        

        var jsonElement = NSDictionary()
        var feeds = [feedStruct]()

        for i in 0 ..< jsonResult.count 
            jsonElement = jsonResult[i] as! NSDictionary

            let feed = feedStruct()
            //the following insures none of the JsonElement values are nil through optional binding
            if let unixstamp = jsonElement["created_at"] as? String 

                let dateFormatter = DateFormatter()
                dateFormatter.dateFormat = "EEE MMM d HH:mm:ss Z yyyy"

                print(unixstamp)

                let date = dateFormatter.date(from: unixstamp)! //THIS LINE IS MAKING THE APP CRASH ON iPHONE NOT SIMULATOR <<<<<<<<<<<<<<<<<<<<<
                let calendar = Calendar.current
                let components = calendar.dateComponents([.year, .month, .day, .hour], from: date)
                let finalDate = calendar.date(from:components)

                let timestamp = finalDate?.timeIntervalSince1970
                let finalTimestamp = String(format: "%.0f", timestamp!)

                feed.date = finalTimestamp
                feed.type = "twitter"   
            
            feeds.append(feed)   
        

        DispatchQueue.main.async(execute:  () -> Void in
            self.delegate.twitterDownloaded(items: jsonResult)
            self.delegate.feedTwitterDatesDownloaded(items: feeds)  
        )
    


【问题讨论】:

有些东西是 nil,找出哪个 var 是 nil。 为什么要让你的类继承自NSObject?这不是 Objective-C,类不需要有基类。您也不应该使用NSDictionary,而是使用它的原生Swift 对应物Dictionary(更具体地说,在处理JSON 数据时使用Dictionary&lt;String:Any&gt;)。 catch let error as NSError print(error) 也是不必要的,你可以简单地做catch print(error)error 变量由catch 块自动提供。您还应该通过在调试器中设置异常断点来将错误定位到单行。 带有unixstamp的设备上打印了什么? 应该的日期 - 这更奇怪@MilanNosáľ 检查我的答案,如果没有帮助,复制粘贴打印结果unixstamp 【参考方案1】:

尝试设置以下(设备的日期/时间设置可能会导致模拟器和设备之间的差异):

let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "EEE MMM d HH:mm:ss Z yyyy"
dateFormatter.timeZone = TimeZone(identifier: "GMT")
dateFormatter.locale = Locale(identifier: "en_US_POSIX")

guard let date = dateFormatter.date(from: unixstamp) else 
    // deal with non-existent date

【讨论】:

根本不应该使用!,这首先是导致崩溃的原因。如果下一个请求为 created_at 返回 nil 怎么办?该应用程序应该能够优雅地失败。一旦它可以做到这一点并且不会崩溃,找出为什么它没有得到想要的值 @Scriptable 如果下一次调用为created_at 返回nil,则整个部分将不会执行(它已经在if let 中),唯一的问题可能导致格式.. 但是是的, 最好优雅地处理可选项.. @D.Finna 当然.. 但要小心隐含的 uwrapping - !,用户最好使用 ?if let 以确保您的应用不会崩溃。您可以在开发模式和测试时使用它 - 开发期间的崩溃让您更容易意识到有问题,但在生产中您希望使用安全操作..

以上是关于在 iPhone 上测试时应用程序崩溃,但在模拟器中没有的主要内容,如果未能解决你的问题,请参考以下文章

什么会导致 iPad(第 3 代)在启动时崩溃但在模拟器中工作?

应用程序在 iPhone 上崩溃,但在模拟器上没有

Flutter App 在模拟器(Iphone 12 mini)上完美运行,但在设备上崩溃(Iphone 8 plus)

iPhone 应用程序在 OS 3.1 不在模拟器中的设备上崩溃

应用程序在模拟器中运行良好,但在 iphone 中崩溃

iPhone 应用程序由于内存不足而崩溃,但在模拟器中运行良好