Основные данные: NSPredicate, содержащий отношение ко многим, не дает результатов при использовании типа хранилища SQLITE - PullRequest
1 голос
/ 24 января 2011

До недавнего времени я использовал Core Data с In-Memory store для своего проекта.Теперь я пытаюсь переключиться на хранилище SQLite и сталкиваюсь со следующей проблемой:

При попытке извлечь объекты из хранилища с использованием предиката и sortDescriptor мой fetchedResultsController возвращает 0 объектов.Тот же самый код прекрасно работает, когда тип хранилища находится в памяти.

Вот как я делаю выборку:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"ANY %K == %@", @"categories", category];
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"title" ascending:YES selector:@selector(caseInsensitiveCompare:)];
self.fetchedResultsController = [self createFetchedResultsControllerWithEntityName : @"Provider" sectionName : @"group" sortDescriptor : sortDescriptor predicate : predicate cache : nil];

NSError *error = nil;
if (![self.fetchedResultsController performFetch:&error]) {
    NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
    abort();
}       

[self.tableView reloadData];

и здесь я создаю запрос на выборку:

- (NSFetchedResultsController *)createFetchedResultsControllerWithEntityName : (NSString*) entityName sectionName : (NSString*) sectionName sortDescriptor : (NSSortDescriptor*) sortDescriptor predicate : (NSPredicate*) predicate cache : (NSString*) cacheName{ 

// Create the fetch request for the entity.
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription *entity = [NSEntityDescription entityForName:entityName inManagedObjectContext:managedObjectContext];
[fetchRequest setEntity:entity];

NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];

[fetchRequest setSortDescriptors:sortDescriptors];

//set predicate 
if (predicate)
    [fetchRequest setPredicate:predicate]; 

// Edit the section name key path and cache name if appropriate.
// nil for section name key path means "no sections".
NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest 
                                                                                                managedObjectContext:managedObjectContext 
                                                                                              sectionNameKeyPath:sectionName 
                                                                                                       cacheName:cacheName];
aFetchedResultsController.delegate = self;

[fetchRequest release];
[sortDescriptor release];
[sortDescriptors release];


return [aFetchedResultsController autorelease];

}

Опять же, этот же код извлекает много объектов при использовании хранилища в памяти, но пустой массив fetchedObjects при использовании SQLite.

Я прочитал документацию Apple относительно особых соображений, которые следует учитывать при использовании предикатов и sortDescritors с хранилищем SQLite.Я использую в предикате одно (многие) отношение ко многим (категориям), так что это должно быть хорошо?

Нет ошибок, возвращаемых из выборки.Просто нет объектов (fetchedResultsController.fetchedObjects пусто).

Любое руководство будет с благодарностью.

Спасибо

Ответы [ 2 ]

1 голос
/ 27 января 2011

Я понял эту проблему в конце концов.

Мой запрос не дал результатов, действительно никаких результатов не было.Возвращаясь к тому месту, где я создавал объекты, и заполняя их значениями, я заметил, что я делал это неправильно.Я попытался сделать:

[provider.categories addObject : newCategory];

, который на самом деле не добавил newCategory к отношениям категорий.
После того, как я понял, что Core Data автоматически создает средства доступа для отношений ко-многим, я использовал следующее, чтобы добавитьnewCategory:

[provider addCategoriesObject : newCategory];

Это правильно добавило newCategory в отношения.

В дополнение к этому я объявил addCategoriesObject в Provider.h для подавления предупреждения компилятора.Это решило проблему для меня.

Единственное оставшееся предупреждение: компилятор не находит реализацию addCategoriesObject: и предупреждает о "неполной реализации".Я не нашел способ подавить это предупреждение тоже.

0 голосов
/ 26 января 2011

Я знаю, что в некоторых магазинах SQLite возникают проблемы с выборками "ANY" (точных я не помню).Может быть, попробуйте изменить свой предикат поиска, чтобы увидеть, если вы получите другие результаты, например,

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"categories LIKE %@", category];
...