无法将“Swift._SwiftDeferredNSDictionary<Swift.String, Swift.String>”类型的值转换为“NSMutableDictionary”

Posted

技术标签:

【中文标题】无法将“Swift._SwiftDeferredNSDictionary<Swift.String, Swift.String>”类型的值转换为“NSMutableDictionary”【英文标题】:Could not cast value of type 'Swift._SwiftDeferredNSDictionary<Swift.String, Swift.String>' to 'NSMutableDictionary' 【发布时间】:2017-11-01 09:42:31 【问题描述】:

我有一个用 Swift 3.0 编写的应用程序,我声明了以下数据类型:

var movies = [Movie]()
var getPlist = NSMutableDictionary()
var movieItems = NSMutableDictionary()

我有以下方法正在加载 plist 的内容:

// Connect to plist and get the data
    if let plist = PlistHandler(name: "MovieData") 
        getPlist = plist.getMutablePlistDict()!

        // Load the movie items into the table view data source
        for i in 0..<getPlist.count 
            movieItems = (getPlist.object(forKey: "Item\(i)") as! NSMutableDictionary) as! [String: String] as! NSMutableDictionary
            let newName = movieItems.object(forKey: "Name")
            let newRemark = movieItems.object(forKey: "Remark")
            if newName as? String != "" 
                movies.append(Movie(name: newName as? String, remark: newRemark as? String)
            )
        
     else 
        print("Unable to get Plist")
    

它从另一个类调用一个名为 getMutablePlistDict() 的方法:

// Get the values from plist -> MutableDirectory
func getMutablePlistDict() -> NSMutableDictionary? 

    let fileManager = FileManager.default

    if fileManager.fileExists(atPath: destPath!) 
        guard let dict = NSMutableDictionary(contentsOfFile: destPath!) else  return .none 
        return dict
     else 
        return .none
    

当我运行应用程序时,出现上述错误(请参阅问题标题)。但这是新的。在 Xcode 8 中,我没有收到此错误。这是什么原因以及我必须如何更改我的代码以避免这种情况?

【问题讨论】:

as! NSMutableDictionary) as! [String: String] as! NSMutableDictionary 的语法太可怕了。错误信息非常清楚。您不能将 Swift 字典转换为 NSMutableDictionary不要在 Swift 中使用 NSMutable... 集合类型。将字典声明为[String:String]。使用var 关键字,您可以免费获得可变性。而不是NSMutableDictionary(contentsOfFile 使用PropertyListSerialization 感谢您的提示! 【参考方案1】:

你可以这样使用:

NSMutableDictionary 更改为[String: Any]

var movies = [Movie]()
var getPlist: [String: Any] = [:]
var movieItems: [String: Any] = [:]


func getMutablePlistDict() -> [String: Any] 
    let fileManager = FileManager.default

    if fileManager.fileExists(atPath: destPath!) 
        if let dict = NSDictionary(contentsOfFile: destPath!) as? [String: Any] 
            return dict
        
     else 
        return [:]
    


if let plist = PlistHandler(name: "MovieData") 
        let getPlist = plist.getMutablePlistDict()

        // Load the movie items into the table view data source
        for i in 0..<getPlist.count 
            if let movieItemsCheck = getPlist["Item\(i)"] as? [String: Any] 
                movieItems = movieItemsCheck
                if let newName = movieItems["Name"] as? String, let newRemark = movieItems["Remark"] as? String, newName != "" 
                    movies.append(Movie(name: newName, remark: newRemark))
                
            
        
     else 
        print("Unable to get Plist")
    

【讨论】:

工作正常,但在 ‚if let dict = ... return dict else return [:]

以上是关于无法将“Swift._SwiftDeferredNSDictionary<Swift.String, Swift.String>”类型的值转换为“NSMutableDictionary”的主要内容,如果未能解决你的问题,请参考以下文章

无法将 createdAt 和 updatedAt 保存为日期时间值,也无法将后端保存为前端

C# 无法将类型为“System.Byte[]”的对象强制转换为类型“System.Data.DataTable

无法将类型为“System.Collections.Generic.List`1[EPMS.Domain.SingleItem]”的对象强制转换为类型“EPMS

无法将 .json 文件从 CSV 下载到 JSON 转换并且无法将 JSON 转换为 CSV

无法将 ReactiveUI 添加到 NUnit 测试项目

“无法将图像数据写入路径” - Laravel 图像干预