Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/url/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios 符合NSCoding的类_Ios_Swift_Plist_Nscoding_File Writing - Fatal编程技术网

Ios 符合NSCoding的类

Ios 符合NSCoding的类,ios,swift,plist,nscoding,file-writing,Ios,Swift,Plist,Nscoding,File Writing,我将以下Person课程符合NSCoding协议 class Person: NSObject, NSCoding{ var age:Int var height: Double var name: String init(age:Int, height: Double, name:String){ self.age = age self.height = height self.name = name

我将以下
Person
课程符合
NSCoding
协议

class Person: NSObject, NSCoding{

    var age:Int
    var height: Double
    var name: String

    init(age:Int, height: Double, name:String){
        self.age = age
        self.height = height
        self.name = name
    }

    func encode(with aCoder: NSCoder){
        aCoder.encode(age, forKey: "age")
        aCoder.encode(height, forKey: "height")
        aCoder.encode(name, forKey: "name")
    }

    required init?(coder aDecoder: NSCoder){
        age = aDecoder.decodeObject(forKey: "age") as! Int **//error**
        height = aDecoder.decodeObject(forKey: "height") as! Double
        name = aDecoder.decodeObject(forKey: "name") as! String
        super.init()
    }


}
然后,我创建了这个类的一个数组。我使用
NSKeyedArchiver
将其归档到plist,一切正常。然而,当我试图取消归档时,我得到了一个错误,它涉及到打开一个可选文件,该文件为零。错误出现在标记的
Person
类中。这是我使用的代码:

 if let people = unarchive(){
            print(people)
 }
以下是取消归档的函数:

func unarchive()->[Person]?{
    let paths = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)
    let documentDirectory = paths[0]
    let path = documentDirectory.appending("ObjectData.plist")
    let fileManager = FileManager.default
    if(!fileManager.fileExists(atPath: path)){
        if let bundlePath = Bundle.main.path(forResource: "ObjectData", ofType: "plist"){
            do{
                try fileManager.copyItem(atPath: bundlePath, toPath: path)
            }catch{
                print("problem copying")
            }
        }
    }
    if let objects = NSKeyedUnarchiver.unarchiveObject(withFile: path){
        if let people = objects as? [Person]{
            return people
        }else{
            return nil
        }
    }else{
        return nil
    }
}

Int
Double
不作为对象存档
aDecoder.decodeObject(forKey:)
对于它们将始终返回
nil
,并使用
作为
nil
将使你的应用程序崩溃

因此,请使用以下方法:

aDecoder.decodeInteger(forKey: "age")
aDecoder.decodeDouble(forKey: "height")

对于
name
字段,您可以保留您的代码。

Int
Double
不作为对象存档
aDecoder.decodeObject(forKey:)
对于它们将始终返回
nil
,并使用
作为
nil
将使你的应用程序崩溃

因此,请使用以下方法:

aDecoder.decodeInteger(forKey: "age")
aDecoder.decodeDouble(forKey: "height")

对于
name
字段,您可以保留您的代码。

您应该使用正确的Int和Double解码方法。您可以在操场中粘贴以下代码并对其进行测试:

import Foundation

class Person: NSObject, NSCoding{

    var age:Int
    var height: Double
    var name: String

    init(age:Int, height: Double, name:String){
        self.age = age
        self.height = height
        self.name = name
    }

    func encode(with aCoder: NSCoder) {
        aCoder.encode(age, forKey: "age")
        aCoder.encode(height, forKey: "height")
        aCoder.encode(name, forKey: "name")
    }

    required init?(coder aDecoder: NSCoder) {
        age = aDecoder.decodeInteger(forKey: "age")
        height = aDecoder.decodeDouble(forKey: "height")
        name = aDecoder.decodeObject(forKey: "name") as! String
        super.init()
    }
}

let john = Person(age: 30, height: 170, name: "John")
let mary = Person(age: 25, height: 140, name: "Mary")

let guys = [john, mary]

let data = NSKeyedArchiver.archivedData(withRootObject: guys)
let people = NSKeyedUnarchiver.unarchiveObject(with: data)

dump (people)

对于Int和Double,应该使用正确的解码方法。您可以在操场中粘贴以下代码并对其进行测试:

import Foundation

class Person: NSObject, NSCoding{

    var age:Int
    var height: Double
    var name: String

    init(age:Int, height: Double, name:String){
        self.age = age
        self.height = height
        self.name = name
    }

    func encode(with aCoder: NSCoder) {
        aCoder.encode(age, forKey: "age")
        aCoder.encode(height, forKey: "height")
        aCoder.encode(name, forKey: "name")
    }

    required init?(coder aDecoder: NSCoder) {
        age = aDecoder.decodeInteger(forKey: "age")
        height = aDecoder.decodeDouble(forKey: "height")
        name = aDecoder.decodeObject(forKey: "name") as! String
        super.init()
    }
}

let john = Person(age: 30, height: 170, name: "John")
let mary = Person(age: 25, height: 140, name: "Mary")

let guys = [john, mary]

let data = NSKeyedArchiver.archivedData(withRootObject: guys)
let people = NSKeyedUnarchiver.unarchiveObject(with: data)

dump (people)