Добавление нескольких записей в набор при сохранении ссылки на объект - PullRequest
0 голосов
/ 21 июня 2011

У меня есть вопрос относительно добавления нескольких записей CoreData в несколько таблиц.

У меня есть следующий код:

while((item = [enumerator nextObject]))
{       
    DOCategory *cat;
    cat = [[self categoryController] getNewCategory];       
    [cat setName:[item objectForKey: @"name"]];
    [cat setDesc:[item objectForKey: @"description"]];
    [cat setLastUpdate:updateTime]; 
    //[[self categoryController] commitChanges];

}

Я использовал для вызоваcommitChanges после каждого перечисления, и это работает, но занимает много времени, особенно на старых устройствах, так как начальная загрузка довольно существенна.Поэтому я просто хочу сохранить в конце всей операции.

Каков наилучший способ добавить все эти возражающие в NSSet (или NSArray) при сохранении ссылки на ManagedContext.Обычно я бы «скопировал» их в набор, но здесь это не работает.Простой вопрос, просто есть блок, чтобы увидеть лучшее решение.

(я предполагаю, что мне не нужно «фиксировать / сохранять» после каждого нового объекта, который я создал, поэтому результаты не записываются вбазы данных еще нет, но они доступны для поиска, поскольку в процедуре присутствуют различные реляционные объекты)


Обновление: после предложения, приведенного ниже, и дополнительного тестирования, мне кажется, что когда я не сохранил / не подтвердилв контекст не включен NSFetchResultController.Это правильно и должно быть так?Есть ли способ выполнить все операции (включая поиск для создания отношений) в «кэше», а затем зафиксировать, как только все будет сделано?


Обновление 2: чтобы получить управляемый объект, у меня естьПроцедура в классе Controller:

- (DOCategory *) getNewCategory{
    return (DOCategory *)[NSEntityDescription insertNewObjectForEntityForName:@"Category" inManagedObjectContext:managedObjectContext];  
}

Кажется, что код работает нормально, включая перекрестные ссылки, пока я не добавлю конечный объект, который использует все другие управляемые объекты.В этом коде должна быть какая-то проблема.

1 Ответ

0 голосов
/ 22 июня 2011

Ваш код старой школы Objective-C 1.0, поэтому было бы лучше обновить его. Вы редко используете напрямую перечислители.

Лучший способ справиться с этим - создать новые управляемые объекты, вставив их в контекст, используя +[NSEntityDescription insertNewObjectForEntityForName:inManagedObjectContext:]. Это создает управляемый объект и информирует о нем контекст. Контекст сохранит сам управляемый объект. Вот откуда происходит «управляемый» из «управляемого объекта».

Обычной практикой при внесении множества изменений является изменение всех объектов, а затем сохранение контекста только после завершения всех изменений.

Обновление:

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

Звучит так, как будто у вас могут быть проблемы с правильной настройкой отношений в самой модели данных. Я не могу сказать наверняка, не зная, как выглядит ваша модель данных.

Я не рекомендую использовать приведение с insertNewObjectForEntityForName:, например,

(DOCategory *)[NSEntityDescription insertNewObjectForEntityForName:@"Category" inManagedObjectContext:managedObjectContext]; 

... потому что, если у вас есть проблема с моделью данных, например, не предоставлено имя класса DOCategory для объекта DOCatergory, приведение будет скрывать проблему. Если класс не определен, метод вернет экземпляр общего класса NSManagedObject или если вы случайно определите неправильный класс для сущности, например, MadeUpClassName вместо DOCategory, тогда приведение заставит среду выполнения обработать возвращенный объект как DOCategory объект. Это может хорошо работать до тех пор, пока в коде нет.

... мне кажется, что когда я не сохранен / зафиксирован контекст это не включен NSFetchResultController. Является это правильно и должно быть кстати? Есть ли способ сделать все операции (включая поиск в создать отношения) в «кэш», а затем совершить, как только все будет сделано?

Не совсем уверен, какую проблему вы видите. Рекомендуется вносить все изменения во все объекты, а затем сохранять контекст вместо сохранения после каждого изменения какого-либо отдельного объекта. Дисковые операции стоят дорого.

Если ваши изменения в контексте не отражены в NSFetchResultsController (FRC), то вы, скорее всего, не реализовали методы делегата FRC, которые обновляют представление таблицы (см. Документацию FRC.) Другая возможная ошибка - это то, что вы создали два контекста случайно. Если вы используете потоки, каждый из которых имеет отдельный контекст (необходимая практика), то вы должны объединить фоновый контекст с передним контекстом, прежде чем изменения, сделанные в фоновом режиме, станут известны на переднем плане.

...