迅速。 SIGABRT:将“__NSCFDictionary”types的值转换为“NSMutableArray”

我正在制作转换器应用程序。 我想保存历史转换。 我看到这个教程,它工作正常,但是当我试图在我的应用程序上使用它,我得到一个SIGABRT。

无法将“__NSCFDictionary”(0x57945c)types的值转换为“NSMutableArray”(0x5791c8)

我得到这个

notesArray = try NSPropertyListSerialization.propertyListWithData(data, options: NSPropertyListMutabilityOptions.MutableContainersAndLeaves, format: nil) as! NSMutableArray

编辑:

AppDelegate中:

 import UIKit @UIApplicationMain class AppDelegate: UIResponder, UIApplicationDelegate { var window: UIWindow? var plistPathInDocument:String = String() func preparePlistForUse(){ let rootPath = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, .UserDomainMask, true)[0] plistPathInDocument = rootPath.stringByAppendingString("/historic.plist") if !NSFileManager.defaultManager().fileExistsAtPath(plistPathInDocument){ let plistPathInBundle = NSBundle.mainBundle().pathForResource("historic", ofType: "plist") as String! do { try NSFileManager.defaultManager().copyItemAtPath(plistPathInBundle, toPath: plistPathInDocument) }catch{ print("Error occurred while copying file to document \(error)") } } } func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool { // Override point for customization after application launch. self.preparePlistForUse() return true } func applicationDidBecomeActive(application: UIApplication) { // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. self.preparePlistForUse() } } 

视图控制器:

 import UIKit class ViewControllerHistorico: UITableViewController { var notesArray:NSMutableArray! var plistPath:String! override func viewWillAppear(animated: Bool) { let appDelegate = UIApplication.sharedApplication().delegate as! AppDelegate plistPath = appDelegate.plistPathInDocument // Extract the content of the file as NSData let data:NSData = NSFileManager.defaultManager().contentsAtPath(plistPath)! do{ notesArray = try NSPropertyListSerialization.propertyListWithData(data, options: NSPropertyListMutabilityOptions.MutableContainersAndLeaves, format: nil) as! NSMutableArray }catch{ print("Error occured while reading from the plist file") } self.tableView.reloadData() } override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell{ let cell:UITableViewCell! = tableView.dequeueReusableCellWithIdentifier("cellIdentifier") cell.textLabel!.text = notesArray.objectAtIndex(indexPath.row) as? String return cell } override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int{ return notesArray.count } override func tableView(tableView: UITableView, commitEditingStyle editingStyle: UITableViewCellEditingStyle, forRowAtIndexPath indexPath: NSIndexPath){ // remove the row from the array notesArray.removeObjectAtIndex(indexPath.row) self.tableView.deleteRowsAtIndexPaths([indexPath], withRowAnimation: UITableViewRowAnimation.Fade) notesArray.writeToFile(plistPath, atomically: true) } } 

historic.plist

你正试图把一个Dictionary转换成一个NSMutableArray

您可以将其保存为字典,将您的代码更改为:

 var notesDict: NSMutableDictionary = try NSPropertyListSerialization.propertyListWithData(data, options: NSPropertyListMutabilityOptions.MutableContainersAndLeaves, format: nil) as! NSMutableDictionary 

相信我有这个相同的问题,并从您的代码看起来像我们也从同一个例子复制。 我准备好了我的plist文件,XCode确实让我的调用成为了一个数组,但是我的数据并不是数组格式的,它是一个字典,它是保存的格式。

当我重新加载plist文件时,NSPropertyListSerialization足够聪明,看到我的数据真的是一个字典,所以强制转换为NSMutableArray失败(BOOM!)。 果然,当我打开保存的plist文件并检查它时,XML清楚地显示它已经被保存为字典。 所以,考虑一下你正在保存的数据,如果它真的是一个字典,改变转换为NSMutableDictionary,并使用该格式解压缩数据。