尝试在Core Data中执行批量删除时实现主子管理对象上下文 [英] Trying to implement master-child Managed Object Context when doing mass delete in Core Data

查看:215
本文介绍了尝试在Core Data中执行批量删除时实现主子管理对象上下文的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在做一个项目,我正在做一个大量的删除NSManagedObjects(MO),我从Core Data检索。当我迭代这个MO的集合,我还通过在MO的初始集合的迭代期间调用获取方法检索其他MO。

I am working on a project where I am doing a mass delete of a number of NSManagedObjects (MO) that I retrieve from Core Data. When I iterate through this collection of MO's, I am also retrieving OTHER MO's by calling a fetch method DURING the iteration of the initial collection of MO's.

如果在此迭代过程中,从提取请求中找到一个对象,则MO将被删除。我意识到这是一个糟糕的架构设计,因为这些MO实际上应该彼此具有反向关系,因此通过级联删除规则,所有这些对象将很容易被删除。这不幸的是不是这样的情况,这将是太难了,回去做这些修复,这就是为什么我在这里。

If during this iteration process, an object is found from the fetch request, the MO is deleted. I realize that this is a poor design of the architecture, as these MO's should in fact be having inverse relationships with one another, and therefore via a cascade delete rule, all of these objects would easily be deleted. This unfortunately is not the case, and it would be too difficult to go back and make these fixes, which is why I am here.

此外,我意识到这个场景,我描述应该使用父子NSManagedObjectContext做事情正确,当然,以避免崩溃发生。我不确定如何实现这给予我正在使用的架构。下面是我使用的代码示例:

Also, I realize that this scenario which I am describing should be using a parent-child NSManagedObjectContext to do things correct, and of course, to avoid crashes from occurring. I am unsure how to implement this given the architecture I am working with. Here is an example of the code I am working with:

- (void)massDelete {

...
       NSArray *objectsToPurge = [self.managedObjectContext executeFetchRequest:fetchRequest error:&error];

       if (objectsToPurge) {

            [objectsToPurge enumerateObjectsUsingBlock:^(MyMO *mo, NSUInteger idx, BOOL *stop) {

                OtherMO *otherMO = [self fetchOtherMO:mo];

                if (otherMO) {
                    [self.managedObjectContext deleteObject:otherMO];
                }

                [self.managedObjectContext deleteObject:mo];

            }];
        }

        [self.managedObjectContext save:&purgeError];
}


    - (OtherMO *)fetchOtherMO:(MyMO *)mo {

        NSManagedObjectContext *context = [[MySingleton sharedInstance] managedObjectContext];
        NSError *error;

        // Create fetch request
        NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
        NSEntityDescription *entity = [NSEntityDescription entityForName:@"OtherMO" inManagedObjectContext:context];
        [fetchRequest setEntity:entity];

        // Create predicate
        NSPredicate *pred = [NSPredicate predicateWithFormat:@"myMO == %@", mo];
        [fetchRequest setPredicate:pred];

        NSArray *items = [context executeFetchRequest:fetchRequest error:&error];
        if ([items count]>0) {
            return [items firstObject];
        } else {
            return nil;
        }
    }

像我说的,我意识到我使用两单独的NSManagedObjectContexts在这里,我需要实现一个父子结构,但我不确定如何做到这一点。考虑到我不能对核心数据架构做任何事情,并且考虑到这是我正在使用的场景,对我的问题最好的解决方案是什么?

Like I said, I realize that I am using two separate NSManagedObjectContexts here, and I need to implement a Parent-Child construct, but am unsure how to do this. Given that I can't do anything about the Core Data architecture, and given this is the scenario I am working with, what would be the best solution for my problem?

感谢所有回复。

推荐答案

我认为它不需要两个MOC,你可以一个解决。只需将它作为参数传递给 fetchOtherMOByMyMo:(MyMo *)mo onContext:(NSManagedObjectContext *)context。

I think it not require two MOC, you are able to solve it by one. Just pass it as a parameter to the fetchOtherMOByMyMo:(MyMo *)mo onContext:(NSManagedObjectContext *)context.

你忘记使用 performBlock:检查,它应该工作不会崩溃:

And you forget to use performBlock: Check, it should work without crashing:

- (void)massDelete {

...
__weak typeof(self) weakSelf = self;
self.managedObjectContext performBlock:^{
       NSArray *objectsToPurge = [weakself.managedObjectContext executeFetchRequest:fetchRequest error:&error];

       if (objectsToPurge) {

            [objectsToPurge enumerateObjectsUsingBlock:^(MyMO *mo, NSUInteger idx, BOOL *stop) {

                OtherMO *otherMO = [weakself fetchOtherMO:mo onContext:weakself.managedObjectContext];

                if (otherMO) {
                    [weakself.managedObjectContext deleteObject:otherMO];
                }

                [weakself.managedObjectContext deleteObject:mo];

            }];
        }

        [weakself.managedObjectContext save:&purgeError];
});
}

- (OtherMO *)fetchOtherMO:(MyMO *)mo onContext:(NSManagedObjectContext *)context{
        NSError *error;

        // Create fetch request
        NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
        NSEntityDescription *entity = [NSEntityDescription entityForName:@"OtherMO" inManagedObjectContext:context];
        [fetchRequest setEntity:entity];

        // Create predicate
        NSPredicate *pred = [NSPredicate predicateWithFormat:@"myMO == %@", mo];
        [fetchRequest setPredicate:pred];

        NSArray *items = [context executeFetchRequest:fetchRequest error:&error];
        if ([items count]>0) {
            return [items firstObject];
        } else {
            return nil;
        }
    }

这篇关于尝试在Core Data中执行批量删除时实现主子管理对象上下文的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆