6

I have following code for fetching and grouping search results:

NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"Song"];
[request setPredicate:[NSCompoundPredicate andPredicateWithSubpredicates:predicates]];
[request setResultType:NSDictionaryResultType];
[request setSortDescriptors: @[[NSSortDescriptor sortDescriptorWithKey:@"timestamp" ascending:YES]]];

NSExpression *countExpression = [NSExpression expressionWithFormat:@"count:(SELF)"];
NSExpressionDescription *expressionDescriprion = [[NSExpressionDescription alloc] init];
[expressionDescriprion setName:@"count"];
[expressionDescriprion setExpression:countExpression];
[expressionDescriprion setExpressionResultType:NSInteger64AttributeType];

NSArray *properties = @[@"artistName", @"songName"];
[request setPropertiesToFetch:[properties arrayByAddingObject:expressionDescriprion]];
[request setPropertiesToGroupBy:properties];

self.fetchedItems = [self.managedObjectContext executeFetchRequest:request error:nil];

which works very nice but I faced to issue and kind of stucked with, so I need to make this propertiesToGroupBy (property type is NSString *) case insensitive somehow. At the moment I have following output:

<_PFArray 0x7fa3e3ed0d90>(
{
    artistName = "System of a Down";
    count = 44;
    songName = "Lonely Day";
},
{
    artistName = "System Of A Down";
    count = 2;
    songName = "Lonely Day";
},
{
    artistName = "System of a Down";
    count = 4;
    songName = "Chop Suey";
}
)

which is incorrect, so I need first 2 items to be in single section, cause this is the same artist.

Is there any way to achieve that?

Cœur
  • 37,241
  • 25
  • 195
  • 267
iiFreeman
  • 5,165
  • 2
  • 29
  • 42

1 Answers1

0

Try using NSExpressionDescription:

NSExpression *artistKeyPathExpression = [NSExpression expressionForKeyPath:@"artistName"];
NSExpression *artistExpression = [NSExpression expressionForFunction:@"uppercase:" arguments:@[artistKeyPathExpression]];
NSExpressionDescription *artistExpressionDescription = [NSExpressionDescription new];
artistExpressionDescription.name = @"groupByArtist";
artistExpressionDescription.expression = artistExpression;
artistExpressionDescription.expressionResultType = NSStringAttributeType;

NSExpression *songKeyPathExpression = [NSExpression expressionForKeyPath:@"songName"];
NSExpression *songExpression = [NSExpression expressionForFunction:@"uppercase:" arguments:@[songKeyPathExpression]];
NSExpressionDescription *songExpressionDescription = [NSExpressionDescription new];
songExpressionDescription.name = @"groupBySongName";
songExpressionDescription.expression = songExpression;
songExpressionDescription.expressionResultType = NSStringAttributeType;

[request setPropertiesToGroupBy:@[artistExpressionDescription, songExpressionDescription]];

Please, note that I can't check this code right now in XCode, so it may contain misprints. Sorry about that, but I think main point is clear.

Borys Verebskyi
  • 4,160
  • 6
  • 28
  • 42
  • That seems impossible to group by NSExpressionDescription for me. After [request setPropertiesToGroupBy: myExpressions]; I always have 'NSInvalidArgumentException', reason: 'Invalid keypath expression – iiFreeman Feb 24 '16 at 20:38