web-dev-qa-db-fra.com

Comment utiliser NSUserDefaults pour stocker un tableau de classes personnalisées dans Swift?

J'ai une classe personnalisée appelée Person qui stocke divers attributs concernant une personne lorsqu'elle entre des informations.

class Person {

    // Person dictionary variable
    var name: String?
    var age: String?
    var html_url: String?

    init(json: NSDictionary) { // Dictionary object
        self.name = json["name"] as? String
        self.age = json["age"] as? String
        self.html_url = json["html_url"] as? String // Location of the JSON file
    }
}

Une fois le dictionnaire créé, il est placé dans un tableau. J'ai des problèmes pour enregistrer le tableau dans NSUserDefaults lorsqu'un bouton est exploité.

personArray.append(newPerson) // newPerson = dictionary of attributes


NSUserDefaults.standardUserDefaults().setObject(personArray, forKey: "personArray")
        NSUserDefaults.standardUserDefaults().synchronize()

J'ai examiné Comment stocker des objets personnalisés dans NSUserDefaults et Enregistrement d'une classe Swift personnalisée avec NSCoding en UserDefaults mais je n'ai pas eu de chance et j'ai du mal à comprendre.

Lorsque j'essaie simplement de sauvegarder dans NSUserDefaults, on me dit ce qui suit:

Attempt to set a non-property-list object (
    "PersonApp.Person"
) as an NSUserDefaults/CFPreferences value for key personArray

Quelqu'un pourrait-il m'aider à sauvegarder un tableau d'objets personnalisés (dictionnaires personnalisés) via NSUserDefaults?

8
Daniel Bramhall

Votre classe Person devrait ressembler à ceci:

Swift 3:

class Person : NSObject, NSCoding{

    // Person dictionary variable
    var name: String?
    var age: String?
    var html_url: String?

    init(json: NSDictionary) { // Dictionary object
        self.name = json["name"] as? String
        self.age = json["age"] as? String
        self.html_url = json["html_url"] as? String // Location of the JSON file
    }

    required init?(coder aDecoder: NSCoder) {

        self.name = aDecoder.decodeObjectForKey("name") as? String;
        self.age = aDecoder.decodeObjectForKey("age") as? String;
        self.html_url = aDecoder.decodeObjectForKey("html") as? String;
    }

    func encodeWithCoder(aCoder: NSCoder) {
        aCoder.encodeObject(self.name, forKey: "name");
        aCoder.encodeObject(self.age, forKey: "age");
        aCoder.encodeObject(self.html_url, forKey: "html");
    }
}

Et voici un exemple de sauvegarde et de récupération du tableau à partir de NSUserDefaults:

let p = Person()
p.name = "person1"
p.age = "12"
p.html_url = "www.google.ro"

let p2 = Person()
p2.name = "person2"
p2.age = "11"
p2.html_url = "www.google.ro"

let array = [p, p2]

let userDefaults = NSUserDefaults.standardUserDefaults()
userDefaults.setValue(NSKeyedArchiver.archivedDataWithRootObject(array), forKey: "persons")
userDefaults.synchronize()

let array : [Person]
array = NSKeyedUnarchiver.unarchiveObjectWithData(userDefaults.objectForKey("persons") as! NSData) as! [Person]
print("\(array[0].name)\(array[1].name)")

Swift 4:

class Person : NSObject, NSCoding{

    // Person dictionary variable
    var name: String?
    var age: String?
    var html_url: String?

    init(json: NSDictionary) { // Dictionary object
        self.name = json["name"] as? String
        self.age = json["age"] as? String
        self.html_url = json["html_url"] as? String // Location of the JSON file
    }

    required init?(coder aDecoder: NSCoder) {
        self.name = aDecoder.decodeObject(forKey: "name") as? String;
        self.age = aDecoder.decodeObject(forKey: "age") as? String;
        self.html_url = aDecoder.decodeObject(forKey: "html") as? String;
    }

    func encode(with aCoder: NSCoder) {
        aCoder.encode(self.name, forKey: "name");
        aCoder.encode(self.age, forKey: "age");
        aCoder.encode(self.html_url, forKey: "html");
    }
}
19
vladiulianbogdan

Vous devez implémenter le protocole NSCoding pour stocker un objet personnalisé dans NSUserDefaults. Découvrez cet exemple http://nshipster.com/nscoding/

5
iMuzahid

Swift 4  

  • Confirmez le protocole codable à votre classe
  • Sérialiser (Data) votre objet en utilisant la classe JsonEncoder
  • Maintenant, sauvegardez vos données sur userDefaults

Voir cette réponse pour avoir une idée claire Enregistrer le tableau d’un objet Custom Swift dans userDefaults

2