gpt4 book ai didi

ios - 删除时 CoreData 崩溃等等

转载 作者:行者123 更新时间:2023-11-28 20:08:21 25 4
gpt4 key购买 nike

我对 CoreData 有一些非常神秘的行为。

我将添加一个对象。我保存这个对象。我获取新结果并重新加载 Collection View (从中显示对象)。新对象出现了。欢呼!正如预期的那样。

我第二次这样做了,但是从现在开始(除非重新启动应用程序)每次从我的 NSFetchedResultsController 重新获取数据并重新加载 Collection View 时,新对象都不会出现。

同样,如果我删除一个对象。第一次,好的!下次我这样做时,应用程序实际上崩溃并出现以下错误:

(Aircraft 是我的 NSManagedObject)

Terminating app due to uncaught exception 'NSObjectInaccessibleException', reason: 'CoreData could not fulfill a fault for '0xd0000000000c0000 <x-coredata://C418948D-90CD-40E9-A502-C4CAB0134419/Aircraft/p3>''
*** First throw call stack:
(0x18b79f09c 0x197ad5d78 0x18b4a77ac 0x18b4a6cac 0x18b4a6b00 0x100034438 0x18e6d8a44 0x18e6d6dc0 0x18e6d2e44 0x18e66ed78 0x18e26b0cc 0x18e265c94 0x18e265b4c 0x18e2653d4 0x18e265178 0x18e25ea30 0x18b75f7e0 0x18b75ca68 0x18b75cdf4 0x18b69db38 0x19106f830 0x18e6dc0e8 0x1000217dc 0x1980bfaa0)
libc++abi.dylib: terminating with uncaught exception of type _NSCoreDataException

是时候编写一些代码了。我看不出有任何问题,但它就在这里。我不会向您发送垃圾邮件,但如果有什么东西响起任何警报,我可以随时根据要求添加它。

从主视图 Controller 开始。这包含我的收藏 View 。请注意,它有两个部分,每个部分从一个单独的 NSFetchedResultsController 中获取数据。不过,我只看到了这个特定问题。相当标准的获取结果 Controller 。

- (NSFetchedResultsController *)aircraftFetchedResultsController
{
if (_aircraftFetchedResultsController != nil) {
return _aircraftFetchedResultsController;
}

NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Aircraft" inManagedObjectContext:self.managedObjectContext];
[fetchRequest setEntity:entity];

// Set the batch size to a suitable number.
[fetchRequest setFetchBatchSize:50];

// Edit the sort key as appropriate.
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:YES];
NSArray *sortDescriptors = @[sortDescriptor];

[fetchRequest setSortDescriptors:sortDescriptors];

// 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:self.managedObjectContext sectionNameKeyPath:nil cacheName:@"Master"];
aFetchedResultsController.delegate = self;
self.aircraftFetchedResultsController = aFetchedResultsController;

NSError *error = nil;
if (![self.aircraftFetchedResultsController performFetch:&error]) {
// Replace this implementation with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}

return _aircraftFetchedResultsController;
}

我在任何使用 NSManagedObjectContext 的地方都从我的 AppDelegate 获取它。添加新对象时,用户处于模态(表单) View Controller 中。我创建了一个新对象,但不立即插入它,以防用户取消:

SLAppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
NSManagedObjectContext *managedObjectContext = appDelegate.managedObjectContext;
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Aircraft" inManagedObjectContext:managedObjectContext];
self.aircraft = [[Aircraft alloc] initWithEntity:entity insertIntoManagedObjectContext:nil];

然后,完成后,保存对象:

SLAppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];

//Only need to insert the new object if its 'NEW' else just save the existing one we are editing
if (!isEditing)
{
//Create new aircraft
NSManagedObjectContext *managedObjectContext = appDelegate.managedObjectContext;
//We are definetly saving the object, so now we insert it
[managedObjectContext insertObject:self.aircraft];
}

//Save
[appDelegate saveContextWithCompletionBlock:^(BOOL didSaveSuccessfully) {
if (didSaveSuccessfully)
{
[self dismissViewControllerAnimated:YES completion:^{
[delegate addAircraftDidSave:YES];
}];
}
else
{
[self dismissViewControllerAnimated:YES completion:^{
//ALERT with error
}];
}
}];

我使用委托(delegate)向主视图 Controller 发送一条消息,说明对象已保存。然后该方法获取新数据并重新加载 Collection View 以显示新对象:

-(void)fetchAircraft
{
NSError *error;
if (![[self aircraftFetchedResultsController] performFetch:&error])
{
// Update to handle the error appropriately.
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
[UIAlertView showGenericErrorAlert];
}
//Success, we have results
else
{
[self.collectionView reloadData];
}
}

完成。正如我所说,这第一次起作用,然后开始行动。同样,你可以用保存代码代替我的删除代码,非常相似,删除并保存更改:

SLAppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
NSManagedObjectContext *managedObjectContext = appDelegate.managedObjectContext;
[managedObjectContext deleteObject:self.aircraft];

[appDelegate saveContextWithCompletionBlock:^(BOOL didSaveSuccessfully) {
if (didSaveSuccessfully)
{
[self dismissViewControllerAnimated:YES completion:^{
[delegate addAircraftDidSave:YES];
}];
}
else
{
//ALERT with error
}
}];

最佳答案

(来 self 上面的评论:) 两个获取的结果 Controller 必须使用不同的缓存(缓存名称: 参数)。我也认为(但我不是 100% 确定)没有部分,缓存没有任何优势,所以你也可以试试 cacheName:nil

关于ios - 删除时 CoreData 崩溃等等,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21211426/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com