Я должен создать NSManagedObject
экземпляры, сделайте некоторый материал с ними и затем повредите их или хранилище к sqlite дб. Проблема, я не могу создать экземпляры NSManagedObject
не связанный с NSManagedObjectContext
и это означает, что я должен разрешить так или иначе после того, как я решаю, что мне не нужны некоторые объекты в моем дб.
Для контакта с ним я создал хранилище в оперативной памяти с помощью того же координатора, и я помещаю временные объекты туда при помощи assignObject:toPersistentStore.
Теперь, как я удостоверяюсь, чтобы эти временные объекты не добирались до данных, которые я выбираю от общего до обоих контекстов хранилищ? Или я должен создать отдельные контексты для такой задачи?
Теперь я думаю о создании отдельного контекста для хранилища в оперативной памяти. Как я перемещаю объекты от одного контекста до другого? Просто с помощью [контекст insertObject:]? Это будет работать хорошо в этой установке? Если я вставляю один объект от графика объектов, целый график также становится вставленным в контекст?
ПРИМЕЧАНИЕ: Этот ответ очень старый. См. Комментарии для полной истории. С тех пор моя рекомендация изменилась, и я больше не рекомендую использовать несвязанные экземпляры NSManagedObject
. Моя текущая рекомендация - использовать временные дочерние экземпляры NSManagedObjectContext
.
Исходный ответ
Самый простой способ сделать это - создать экземпляры NSManagedObject
без связанного NSManagedObjectContext
.
NSEntityDescription *entity = [NSEntityDescription entityForName:@"MyEntity" inManagedObjectContext:myMOC];
NSManagedObject *unassociatedObject = [[NSManagedObject alloc] initWithEntity:entity insertIntoManagedObjectContext:nil];
Затем, когда вы захотите его сохранить:
[myMOC insertObject:unassociatedObject];
NSError *error = nil;
if (![myMoc save:&error]) {
//Respond to the error
}
Правильный способ добиться такого рода вещей - использовать новый контекст управляемого объекта. Вы создаете контекст управляемого объекта с тем же постоянным хранилищем:
NSManagedObjectContext *tempContext = [[[NSManagedObjectContext alloc] init] autorelease];
[tempContext setPersistentStore:[originalContext persistentStore]];
Затем вы добавляете новые объекты, изменяете их и т. Д.
Когда приходит время сохранять, вам нужно вызвать [tempContext save: ...] в tempContext и обработайте уведомление о сохранении, чтобы объединить его с исходным контекстом. Чтобы отбросить объекты, просто отпустите этот временный контекст и забудьте о нем.
Таким образом, когда вы сохраняете временный контекст, изменения сохраняются в хранилище, и вам просто нужно вернуть эти изменения обратно в ваш основной контекст:
/* Called when the temp context is saved */
- (void)tempContextSaved:(NSNotification *)notification {
/* Merge the changes into the original managed object context */
[originalContext mergeChangesFromContextDidSaveNotification:notification];
}
// Here's where we do the save itself
// Add the notification handler
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(tempContextSaved:)
name:NSManagedObjectContextDidSaveNotification
object:tempContext];
// Save
[tempContext save:NULL];
// Remove the handler again
[[NSNotificationCenter defaultCenter] removeObserver:self
name:NSManagedObjectContextDidSaveNotification
object:tempContext];
Таким же образом вы должны обрабатывать многопоточные операции с основными данными . Один контекст на поток.
Если вам нужно получить доступ к существующим объектам из этого временного контекста (для добавления отношений и т. Д.), Вам нужно использовать идентификатор объекта, чтобы получить новый экземпляр, например:
NSManagedObject *objectInOriginalContext = ...;
NSManagedObject *objectInTemporaryContext = [tempContext objectWithID:[objectInOriginalContext objectID]];
Если вы попытаетесь использовать NSManagedObject
в неправильном контексте вы получите исключения при сохранении.