2009-10-20 51 views
6

我有一个名为importMoc的内存管理对象上下文,我用它来导入记录(例如雇员)。我已经解析了一个文件,并在importMoc中设置了一个非常重要的异常。用户确认他们想要处理%d员工,但我无法弄清楚如何或何时设置员工的“父母”关系(例如设置其部门)。在导入核心数据时建立关系?

为了我的目的,他们都将被导入到同一个部门(用户已经隐式选择)。

很明显,我不能设置在两个上下文中的关系,这样做我:

  1. 创建importMoc一个部门,然后当我合并更改合并与“真正的”部门“进口”处?
  2. 2)合并员工,然后获取所有刚进口的员工(不知何故!!!),然后设置他们的部门?
  3. 3)我忽略了一些其他解决方案?

这似乎是一个简单的问题,但由于某种原因(懒惰?疲倦?愚蠢?)我无法弄清楚如何去做!到目前为止我尝试过的所有东西似乎太复杂了!

在此先感谢!

回答

0

1 /假定雇员记录X具有名称Y和部门ID 15(即,它经由一个关系是指id为15处)从被管理对象的上下文与部门ID 15

2 /负载部

3 /创建引用在(2)

即创建对象雇员(注:样品代码只,可能不会编译):

NSEntityDescription * departmentED = [NSEntityDescription entityForName:@"Department" inManagedObjectContext:moc]; 
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(id == %@)", deptId]; 

NSFetchRequest *request = [[[NSFetchRequest alloc] init] autorelease]; 
[request setEntity:departmentED]; 
[request setPredicate:predicate]; 

NSError *error = nil; 
NSArray *array = [moc executeFetchRequest:request error:&error]; 

/* create employee */ 

NSEntityDescription * employeeED = [NSEntityDescription entityForName:@"Employee" inManagedObjectContext:moc]; 
NSManagedObject * employeeMO = [[[NSManagedObject alloc] initWithEntity:employeeED insertIntoManagedObjectContext:moc] autorelease]; 

/* set employee department to department instance loaded above */ 
[receiptObject setValue:[array objectAtIndex:0] forKey:@"department"]; 
+0

感谢diciu,但这并没有回答我关于在两个不同的上下文之间建立关系的最佳方式的问题(如Core中推荐的数据编程指南 - 高效导入数据)。 由于时间限制,我目前停止使用第二个托管对象上下文进行导入,但我仍然很想知道正确的方法。 我还发现了以下最近的问题,但提供的答案不是很令人满意: http:// stackoverflow。com/questions/1554623/illegal-attempt-to-establish-a-relationship-xyz-between-objects-in-different-co – Matthew 2009-10-21 03:09:41

4

如果Department对象已被保存到持久性存储中,则可以将它们带入另一个托管对象上下文。因为无论如何你的对象都必须住在同一个持久存储中(因为不允许跨商店关系),你应该能够简单地将你需要的对象取回到importMoc中。

例如:

foreach (NSDictionary *record in employeeRecords) { 
    NSManagedObject *employee = [NSEntityDescription insertNewObjectForEntityForName:@"Employee" inManagedObjectContext:importMoc]; 
    // Configure employee however you do that 

    NSString *managerID = [record objectForKey:@"someKeyThatUniquelyIdentifiesTheManager"]; 
    NSFetchRequest *managerFetchRequest = [[NSFetchRequest alloc] init]; 
    [managerFetchRequest setEntity:[NSEntity entityForName:@"Manager" inManagedObjectContext:importMoc]]; 
    [managerFetchRequest setPredicate:[NSPredicate predicateWithFormat:@"managerProperty == %@", managerID]]; 
    NSArray *managers = [importMoc executeFetchRequest:managerFetchRequest error:nil]; // Don't be stupid like me and catch the error ;-) 
    [managerFetchRequest release]; 

    if ([managers count] != 1) { 
     // You probably have problems if this happens 
    } 

    [employee setValue:[managers objectAtIndex:0] forKey:@"manager"]; 
} 

你也可以只是做一个单一的读取请求得到所有的管理人员到importMoc,然后筛选阵列来定位每一次正确的。这可能会更有效率。换句话说,不要做我刚刚告诉你做的事情:-)

+0

因此,阅读精细的手册: 如果我放弃你说的忽略的谓词并调用[importMoc executeFetchRequest:error:]我将得到一个数组,其中包含已保存到持久性存储区的所有管理器(无论其上下文如何),无论它们是否已保存,都会加上当前(importMoc)上下文中的任何管理器,不。 我的理解是否正确? – Matthew 2009-10-22 01:00:03

+0

正确。上下文只在对象在内存中时很重要。一旦它们被保存到持久性存储中,就可以将它们提取到任何上下文中。 – Alex 2009-10-22 04:55:07

+0

只是一个快速的说明,非常感谢这个答复亚历克斯。如果具有相同的持久性存储协调器,我还没有意识到提取会将对象添加到单独的上下文中。我有这个相同的问题,这个答案对我来说是一种享受! – 2010-05-07 13:16:03