Как использовать NSPredicate для фильтрации на основе дочерних элементов?

#objective-c #core-data #nspredicate

#objective-c #core-data #nspredicate

Вопрос:

Я использую Core Data; допустим, у меня есть отношение «многие к одному» между сотрудниками и отделами, и сотрудники хранятся в NSSet в каждом отделе. Я хочу найти все отделы, в которых работает только один сотрудник. Как мне сделать это с Core Data?

Я попробовал приведенный ниже код и получаю исключение, в котором говорится, что MYEmployee не отвечает на allObjects .

 NSPredicate *predicate = [NSPredicate predicateWithFormat:@"ANY SELF.employees.allObjects.count == 1"];
singleEmployeeDepartments = [[myModelController allDepartments] filteredArrayUsingPredicate:predicate]];
  

Комментарии:

1. Весь приведенный выше блок кода состоит из одной строки. Когда я пытаюсь начать следующую строку с singleEmployeeDepartments, это нарушает уценку кода. Что дает?

2. Обратные ссылки предназначены только для форматирования встроенного кода. Для многострочных блоков кода делайте отступ в каждой строке на 4 пробела. Вы также можете выделить текст и нажать {} над полем редактирования или элементом управления-K.

Ответ №1:

Прежде всего, вы неэффективно используете Core Data здесь, потому что вы всегда извлекаете все отделы из хранилища данных, а затем фильтруете результирующий массив в памяти. Вы можете напрямую запрашивать контекст управляемого объекта для поиска соответствующих отделов вместо выборки всех отделов, что может снизить потребление памяти, а также может быть быстрее, если у вас много отделов.

 NSManagedObjectContext *moc = ...;
NSFetchRequest *request = [[[NSFetchRequest alloc] init] autorelease];
[request setEntity:[NSEntityDescription entityForName:@"Department" inManagedObjectContext:moc]];
[request setPredicate:[NSPredicate predicateWithFormat:@"employees.@count == 1"]];
NSArray *singleEmployeeDepartments = [moc executeFetchRequest:request error:NULL];
  

Другой ключевой частью является использование @count оператора в строке предиката для запроса отделов, в которых есть определенное количество сотрудников.

Комментарии:

1. спасибо, это сработало, и спасибо за совет по повышению эффективности. Мне уже нужно запрашивать весь массив для другой цели. Также я думал, что NSSet не реагирует на count, но я думаю, поскольку он находится в NSPredicate и является агрегатной функцией, он работает?

2. Небольшой вопрос: где задокументирован @count? Здесь оно используется косвенно developer.apple.com/library/ios/documentation/Cocoa/Conceptual /…