2017-07-04 6 views
0

Ich habe ein NSSet von Büchern, die in einer Viele-zu-Eins-Beziehung zu einem Autorenobjekt in Kerndaten stehen.IOS/Objective-C/CoreData: Objekt aus NSSet löschen

Es gibt eine Ansicht, in der der Benutzer diese bearbeiten kann, einschließlich der leeren Felder. Der Benutzer kann auch neue hinzufügen. Dies führt zu einer Situation, in:

1) wir die gleiche Anzahl von Büchern am Ende, bearbeiten nur 2) wir mit weniger Büchern am Ende, was bedeutet, einige aus dem NSSet gelöscht werden sollen 3) wir mit am Ende mehr Bücher, was bedeutet, dass einige zum NSSet hinzugefügt werden sollten.

Mein ursprünglicher Ansatz bestand darin, die Elemente in ein NSMutableArray zu konvertieren, Änderungen im muablearray vorzunehmen, zurück in ein NSSet zu konvertieren und das NSSet mit dem Objekt in Beziehung zu setzen.

Während dies im Objektdiagramm der Kerndaten funktioniert, scheint es jedoch nicht die tatsächlichen zugrunde liegenden Objekte im persistenten Speicher zu löschen.

Da NSSet keinen Index enthält, kann ich alternativ keine Möglichkeit zum Löschen eines bestimmten Objekts im NSSet identifizieren.

Der folgende Code ändert die Namen der Bücher unter der Annahme, dass sich die Anzahl der Bücher nicht ändert. Wenn jedoch die Anzahl der Bücher nach der Bearbeitung weniger ist, löscht das fehlende Buch nicht den persistenten Speicher. Es ändert nur die zugehörigen Objekte im Objektdiagramm der Kerndaten. Dies führt zu Problemen, wenn ich den persistenten Speicher mit einem Server synchronisiere.

Also im Grunde suchen nach Weg, ein Element in einem NSSet in Abwesenheit eines Index zu identifizieren und zu löschen. Danke für Anregungen.

NSSet *booksForAuthor = _author.books; 
    NSMutableArray *theBooks = [[booksForAuthor allObjects] mutableCopy]; 

    NSSortDescriptor *sortDescriptor= [[NSSortDescriptor alloc] initWithKey:@"bid" 
               ascending:YES]; 
    NSArray *booksArray = [theBooks sortedArrayUsingDescriptors:@[sortDescriptor]]; 
    _numStartingBooks = [booksArray count]; 
    _booksOnLoad = booksArray; //Now have an array of books before edit 
NSMutableArray <NSString*> *bookNames=[NSMutableArray arrayWithCapacity:20]; 
    //now collect new set of books from user into array (code omitted) 
    [bookNames removeObject:@""];//remove any blanks 
    _numBooks = [bookNames count];//number of books after edit 
    int i; 
     for (i = 0; i < _numStartingBooks; i++) { 
      [theNewBooks addObject:_booksOnLoad[i]]; 
      theNewBooks[i].name = bookNames[i]; 
     }  
    NSSet *theBookSet = [NSSet setWithArray:theNewBooks]; 
    _author.books = theBookSet; 

An dieser Stelle haben wir die NSSet auf die neue Anzahl der Bücher festgelegt, sondern von dem, was ich sagen kann, nicht die zugrunde liegenden zusätzlichen verwalteten Objekte, die am Anfang gelöscht.

Antwort

0

Ich denke, vielleicht ist Ihre gesamte Herangehensweise und Architektur zu kompliziert.

Zunächst laden Sie bitte this sample project from Apple herunter. Falls Apple den Link unterbricht, suchen Sie danach. Es heißt CoreDataBooks. Nimm dir einen oder zwei Tage Zeit, um es zu studieren. Sie sehen, dass es in Objective-C geschrieben ist, wie Ihr Code. Und wie Ihr Projekt hat es Bücher und Autoren. CoreDataBooks ist so ziemlich das perfekte Beispiel für Sie!

Ich empfehle dies, weil es scheint, dass Ihr Code diese NSMutableSets und NSMutableArrays zwischen Ihrer Ansicht und Ihrem Modell (Core Data) zwischenordnet. Du solltest das nicht tun müssen. Tatsächlich habe ich gerade das Apple-Projekt nach den Symbolen NSSet, NSMutableSet, NSArray und NSMutableArray durchsucht. Ich habe nur eins gefunden, eine Reihe von Sortierdeskriptoren! In Apples Beispielprojekt gibt es keine Mengen oder Arrays von Autoren oder Büchern.

Für die Synchronisierung von Daten mit einem Server wird dies durch Erstellen eines sekundären verwalteten Objektkontexts erreicht, der mit demselben persistenten Speicher verbunden ist. In einem richtigen Design wird es überhaupt nicht in Ihre Benutzerschnittstelle einbezogen, also machen Sie sich jetzt keine Sorgen darüber. Lassen Sie Ihre Benutzeroberfläche zuerst mit dem lokalen Core Data Store arbeiten, wie in CoreDataBooks, und bis dahin werden Sie viel gelernt haben und in einer viel besseren Position sein, um die Synchronisierung zu bewältigen :)

Verwandte Themen