使用核心数据检索更多内容时按一个属性分组

Ste*_*mer 8 core-data objective-c ios

我在Core Data中有一个表,其中包含以下属性:

date, name, phone
Run Code Online (Sandbox Code Playgroud)

我想检索5个唯一的电话号码列表,其名称按日期排序.所以在MySQL中它会是这样的:

SELECT name, phone FROM myTable GROUP BY phone ORDER BY date   
Run Code Online (Sandbox Code Playgroud)

所以,如果我有这个数据列表:

01/23/2015 someName1 12345678
01/21/2015 someName2 12345678
01/21/2015 someOtherName1 987654321
Run Code Online (Sandbox Code Playgroud)

我想检索一个唯一电话号码列表,其中日期字段控制与任何重复号码相关联的名称.在这种情况下,期望的结果将是:

01/23/2015 someName1 12345678
01/21/2015 someOtherName1 987654321
Run Code Online (Sandbox Code Playgroud)

但是这样做NSFetchRequest有点复杂,因为setPropertiesToGroupBy需要包含相同的属性列表setPropertiesToFetch.

换句话说,这就是我认为我能够做到的方式:

    NSEntityDescription *entity = [NSEntityDescription  entityForName:@"someEntity" inManagedObjectContext:someContext];
    NSFetchRequest *request = [[NSFetchRequest alloc] init];
    [request setEntity:entity];
    [request setResultType:NSDictionaryResultType];

    [request setPropertiesToFetch:@[@"name", @"phone"]];
    [request setPropertiesToGroupBy:@[@"phone"]];
    [request setFetchLimit:5];

    NSSortDescriptor *sortByCreatedDate = [[NSSortDescriptor alloc] initWithKey:@"date" ascending:NO];
    [request setSortDescriptors:@[sortByCreatedDate]];
Run Code Online (Sandbox Code Playgroud)

但是,propertiesToGroupBy除非我也包含该name字段,否则我将获得例外.

如何在不必手动浏览列表的情况下实现我想要的目标?

pba*_*sdf 6

附带条件我认为这将有效; 我留给你测试它死了:

propertiesToFetch除了那些之外,你不能添加任何其他属性propertiesToGroupBy,但似乎你可以objectID在要获取的属性中包含它们.为此,请为"已评估对象" 构建NSExpression并关联NSExpressionDescription:

NSExpression *selfExp = [NSExpression expressionForEvaluatedObject];
NSExpressionDescription *selfED = [[NSExpressionDescription alloc] init];
selfED.name = @"objID";
selfED.expression = selfExp;
selfED.expressionResultType = NSObjectIDAttributeType;
Run Code Online (Sandbox Code Playgroud)

现在定义另一个表达式/描述以获得max(date):

NSExpression *maxDate = [NSExpression expressionForKeyPath:@"date"];
NSExpression *indexExp = [NSExpression expressionForFunction:@"max:" arguments:@[maxDate]];
NSExpressionDescription *maxED = [[NSExpressionDescription alloc] init];
maxED.name = @"maxDate";
maxED.expression = indexExp;
maxED.expressionResultType = NSDateAttributeType;
Run Code Online (Sandbox Code Playgroud)

然后在要获取的属性列表中包含这两个表达式描述:

[request setPropertiesToFetch:@[@"phone", maxED, selfED]];
[request setPropertiesToGroupBy:@[@"phone"]];
Run Code Online (Sandbox Code Playgroud)

运行fetch时,结果数组中的每个项都将包含一个键"objID",其中包含相关对象的objectID.您可以通过以下方式解压缩,访问姓名,电话等:

NSArray *results = [self.context executeFetchRequest:request error:&error];
for (NSDictionary *dict in results) {
    NSDate *maxDate = dict[@"maxDate"];
    NSString *phone = dict[@"phone"];
    NSManagedObjectID *objID = [dict valueForKey:@"objID"];
    NSManagedObject *object = [self.context objectWithID:objID];
    NSString *name = [object valueForKey:@"name"];
}
Run Code Online (Sandbox Code Playgroud)

我不确定的一个特殊方面是,如果两行完全相同,它将如何表现date.