Données de base: Comment vérifier la présence de relations plusieurs à plusieurs

StackOverflow https://stackoverflow.com/questions/1406565

  •  05-07-2019
  •  | 
  •  

Question

J'ai un "Song" Entité et un " Tag " entité et ils ont une relation plusieurs à plusieurs entre eux. Un morceau peut avoir plusieurs étiquettes et une étiquette peut être appliquée à plusieurs chansons.

Je veux vérifier si une chanson est associée à un morceau. Si la chanson est associée au tag, je souhaite afficher une coche dans la vue tableau.

Pour une logique similaire, dans Apple "TaggedLocations" Dans l'exemple de code, la vérification suivante est effectuée pour vérifier la présence de la relation.

if ([event.tags containsObject:tag]) {
    cell.accessoryType = UITableViewCellAccessoryCheckmark;
}   

Cela peut être inefficace s'il y a beaucoup de balises dans la base de données, car cela les extraira toutes dans la mémoire. S'il vous plaît, corrigez-moi si je me trompe ici.

Existe-t-il un moyen plus efficace de vérifier si le morceau est associé à une étiquette particulière au lieu de l’enregistrer dans Song.Tags?

Était-ce utile?

La solution

C'est en fait assez facile à faire, si complètement sans papiers. Vous voulez créer une demande d'extraction avec un prédicat qui a une opération définie. Si nous imaginons que votre modèle de balise possède une propriété appelée tagValue, le prédicat qui vous tient à cœur est "ANY taggy.tagValue == 'footag'" / ";

NSString *tagSearch = @"footag";

// However you get your NSManagedObjectContext.  If you use template code, it's from
// the UIApplicationDelegate
NSManagedObjectContext *context = [delegate managedObjectContext];

// Is there no shortcut for this?  Maybe not, seems to be per context...
NSEntityDescription *songEntity = [NSEntityDescription entityForName:@"Song" inManagedObjectContext:context];

NSFetchRequest *request = [[NSFetchRequest alloc] init];
[request setEntity:songEntity];

// The request looks for this a group with the supplied name
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"ANY tags.tagValue == %@", tagSearch];
[request setPredicate:predicate];

NSError *error = nil;
NSArray *results = [context executeFetchRequest:request error:&error];

[request release];

Autres conseils

Vous avez raison, utiliser ce code permet de récupérer l'ensemble complet et la comparaison d'objet peut s'avérer assez complexe, en fonction du nombre de propriétés et de relations faisant partie de l'entité de l'objet.

Quoi qu’il en soit, vous ne pouvez pas éviter une comparaison définie pour inclusion. Le mieux que vous puissiez faire est probablement d'éviter d'extraire toutes les propriétés / relations en demandant à Core Data de ne récupérer que les objets NSManagedObjectID.

NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init]; 
[fetchRequest setEntity:[NSEntityDescription entityForName:@"Tag" inManagedObjectContext:[self managedObjectContext]]]; 
[fetchRequest setResultType:NSManagedObjectIDResultType];

Les objets NSManagedObjectID sont garantis comme étant uniques. Par conséquent, vous pouvez les utiliser en toute sécurité pour vérifier l’inclusion des ensembles. Cela devrait être beaucoup plus efficace du point de vue des performances.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top