【问题标题】:Retrieving count of a core data relation检索核心数据关系的计数
【发布时间】:2013-08-25 02:33:20
【问题描述】:

我到处搜索,但找不到我要找的确切内容。我的问题与此类似,但略有不同:

Core Data - Count of Related Records

假设我有一个 Car 实体,它与 Person 实体具有一对多关系。这意味着这辆车可以有多个人驾驶,但每个人只能驾驶一辆车。

我希望能够只执行一个谓词,其中我可以实现以下目标:

  1. 所有“红色”的汽车。
  2. 仅返回匹配汽车的“年份”和“颜色”属性。
  3. 返回驾驶这辆车的人数(即每辆生成的汽车内的 NSSet 人数)。

是否可以通过一个查询完成所有这些操作?

我知道如何处理多个查询。我只会使用setPropertiesToFetch 并使用过滤谓词来实现上面的 1 和 2。然后,我将对每辆车的 Persons 实体执行另一个计数查询 (countForFetchRequest),以找出每辆车有多少人驾驶。

关键是上面的第三个要求。我想在一个谓词中完成所有事情,并且我不想在初始查询时将所有 Person 实体对象都带入内存(性能)。此外,为每辆车调用另一个 countForFetchRequest 查询会很痛苦。

最好的方法是什么?

谢谢!

【问题讨论】:

    标签: ios objective-c core-data nspredicate


    【解决方案1】:

    我目前无法对此进行测试,但应该可以通过将以下表达式描述添加到“要获取的属性”中:

    NSExpression *countExpression = [NSExpression expressionForFunction: @"count:" arguments: [NSArray arrayWithObject:[NSExpression expressionForKeyPath: @"drivers"]]];
    NSExpressionDescription *expressionDescription = [[NSExpressionDescription alloc] init];
    
    [expressionDescription setName: @"driversCount"];
    [expressionDescription setExpression: countExpression];
    [expressionDescription setExpressionResultType: NSInteger32AttributeType];
    

    【讨论】:

    • 您还需要发送[fetchRequest setResultType:NSDictionaryResultType];,并在创建表达式描述后调用[fetchRequest setPropertiesToFetch:@[expressionDescription]];
    • @Abizern:你当然是对的。但是 OP 在他的问题中说他已经知道如何使用 setPropertiesToFetch 来获取年份和颜色属性,因此我省略了这部分。
    • 只需为下一个查看此问题并看到您的答案的人填写它:)
    【解决方案2】:
    1. 只退回“红色”汽车:

      NSPredicate *predicate = [NSPredicate predicateWithFormat:@"color LIKE 'red'"];
      
    2. 返回驾驶这辆车的人数:

      NSExpression *keyPathExpression = [NSExpression expressionForKeyPath:@"people"];
      NSExpression *countExpression = [NSExpression expressionForFunction:@"count:"
                                                                arguments:@[keyPathExpression]];
      
      NSExpressionDescription *expressionDescription = [[NSExpressionDescription alloc] init];
      [expressionDescription setName:@"count"];
      [expressionDescription setExpression:countExpression];
      [expressionDescription setExpressionResultType:NSInteger32AttributeType];
      
    3. 仅返回“年份”和“颜色”属性(以及计数):

      NSEntityDescription *entity = [NSEntityDescription entityForName:@"Car"
                                                inManagedObjectContext:context];
      
      NSDictionary *attributes = [entity attributesByName];
      
      NSArray *properties = @[expressionDescription, attributes[@"year"], attributes[@"color"]];
      
    4. 构建并执行获取请求:

      NSFetchRequest *request = [[NSFetchRequest alloc] init];
      [request setEntity:entity];
      [request setResultType:NSDictionaryResultType];
      
      [request setPropertiesToFetch:properties]; // return only count, year & color
      
      [request setPredicate:predicate]; // return only red cars
      
      NSError *error = nil;
      NSArray *results = [context executeFetchRequest:request error:&error];
      
    5. 处理结果:

      if (results) {
          for (NSDictionary *result in results) {
              NSLog(@"Year: %@", result[@"year"]);
              NSLog(@"Color: %@", result[@"color"]);
              NSLog(@"Drivers: %@", result[@"count"]);
          }
      }
      else {
          NSLog(@"Error: %@", error);
      }
      

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多