I\'m currently trying to sort my array of objects into day order so they can be grouped in the correct order i.e. Monday, Tuesday, Wednesday then by start time.
Only
I was working with the same requirements for custom sorting of sections and Solution #1 worked for me very well, thanks!
One thing I'd like to add is that after adding the transient property if your app crashes mysteriously a couple of seconds after loading, you need to reset your database.
NSError *error;
NSURL *applicationDocumentsDirectory = [[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject];
NSURL *databaseURL = [applicationDocumentsDirectory URLByAppendingPathComponent:@"My Database Name"];
[[NSFileManager defaultManager] removeItemAtPath:databaseURL.path error:&error];
Hope this helps!
I see two solutions:
UPDATE 2 Example code for option 2:
-Change the "day" attribute to a number (Int16) and add a transient (non-persistant) "dayName" string attribute.
-Add this enumeration of the week days:
typdef enum {
kMonday,
kTuesday,
kWednesday,
kThursday,
kFriday,
kSaturday,
kSunday
} WeekDay;
-Set the "day" property of your managed objects to be NSNumber objects. For example:
object.day = [NSNumber numberWithInteger:kMonday];
-Implement the getter function for the transient "dayName" property:
- (NSString*)dayName {
switch ((WeekDay)self.day.integerValue) {
case kMonday:
return @"Monday";
break;
case kTuesday:
return @"Tuesday";
break;
case kWednesday:
return @"Wednesday";
break;
case kMonday:
return @"Monday";
break;
case kThursday:
return @"Thursday";
break;
case kFriday:
return @"Friday";
break;
case kSaturday:
return @"Saturday";
break;
case kSunday:
return @"Sunday";
break;
}
}
-In the fetch request, sort by "day" and use "dayName" as the section name key path.
UPDATE
Note: Option 1 works fine for sorting an array, but Core Data is throwing an 'NSInvalidArgumentException' exception for 'unsupported NSSortDescriptor selector: weekdayCompare:'
Example code for option 1:
// category on NSString for custom comparison
@interface NSString (WeekdayComparison)
- (NSComparisonResult)weekdayCompare:(NSString*)otherDay;
@end
@implementation NSString (WeekdayComparison)
- (NSComparisonResult)weekdayCompare:(NSString*)otherDay {
NSArray *weekDays = [NSArray arrayWithObjects:@"Sunday", @"Monday", @"Tuesday", @"Wednesday", @"Thursday", @"Friday", @"Saturday", nil];
NSUInteger selfIndex = [weekDays indexOfObject:self];
NSUInteger otherDayIndex = [weekDays indexOfObject:otherDay];
if (selfIndex < otherDayIndex) {
return NSOrderedAscending;
}
else if (selfIndex > otherDayIndex) {
return NSOrderedDescending;
} else {
return NSOrderedSame;
}
}
@end
To use the new comparison method:
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"day" ascending:YES selector:@selector(weekdayCompare:)];
NSArray *sortDescriptors = [NSArray arrayWithObjects:sortDescriptor, nil];
[sortDescriptor release];