Параметры сортировки ключа словаря - альфа, затем цифра - PullRequest
1 голос
/ 17 февраля 2012

Все,

Я бы хотел отсортировать этот изменчивый словарь ключей массивов следующим образом: AZ 0-9, но он возвращается, отсортированный 0-9 AZ.Как я могу отсортировать это так, чтобы альфа-символы предшествовали числам?Возможно, есть встроенный метод, который делает это, или я должен создать категорию, которая расширяет NSString?

    NSArray *sKeysArray = [[listContent allKeys] sortedArrayUsingSelector:@selector(caseInsensitiveCompare:)];
    NSString *sectionKey = [sKeysArray objectAtIndex:section];
    NSArray *sectionValues = [listContent valueForKey:sectionKey];

Ответы [ 2 ]

4 голосов
/ 17 февраля 2012

К сожалению, в NSString нет метода, который бы делал это напрямую. Вместо того, чтобы писать категорию, я бы просто использовал NSArray s sortedArrayUsingComparator: метод:

NSArray *sKeysArray = [[listContent ALlKeys] sortedArrayUsingComparator:^(id obj1, id obj2) {
// Code to compare obj1 and obj2 and return an NSComparisonResult here; return NSOrderedAscending if obj1 should come before obj2 
}];

Для каждого сравнения я бы использовал NSString – enumerateSubstringsInRange:options:usingBlock:, передавая NSStringEnumerationByComposedCharacterSequences для опций (в основном перечисление символов, за исключением того, что последовательности символов Юникода, которые на самом деле представляют собой одну «букву», объединяются). И когда вы сравниваете два символа, используйте что-то вроде ответа на этот вопрос , чтобы определить, когда obj1 - это число, а obj2 - обычная буква, и вернуть NSOrderedDescending, в противном случае просто используйте обычный compare:.

2 голосов
/ 17 февраля 2012

Как говорит @yuri, sortedArrayUsingComparator: должен обеспечивать базовую функциональность.

Вот простая версия, которая сортирует строки, начинающиеся с десятичной цифры после строк, начинающихся с буквенного символа (в определении NSCharacterSet), и оставляет все другие комбинации строк в порядке сортировки по умолчанию:

NSArray *arr = [NSArray arrayWithObjects:
                 @"ABC 09 GHJ", @"DEF23PO", @"123ABC", @"MCMLXV", @"[cocoa]", @"$2000", @"ERT", @"24seven", @"zero",
                @"Ångström", @"Übernacht",
                nil];

NSCharacterSet *digits    = [NSCharacterSet decimalDigitCharacterSet];
NSCharacterSet *alphanums = [NSCharacterSet alphanumericCharacterSet];

NSArray *sorted = [arr sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2) {

    if ( [obj1 isKindOfClass:[NSString class]] && [obj1 length] > 0
        && [obj2 isKindOfClass:[NSString class]] && [obj2 length] > 0 ) {

        unichar c1 = [obj1 characterAtIndex:0];
        unichar c2 = [obj2 characterAtIndex:0];

        if ( [digits characterIsMember:c1] && (![digits characterIsMember:c2] && [alphanums characterIsMember:c2]) ) {
            return NSOrderedDescending;
        }

        if ( [digits characterIsMember:c2] && (![digits characterIsMember:c1] && [alphanums characterIsMember:c1]) ) {
            return NSOrderedAscending;
        }
    }

    return [obj1 compare: obj2];
}];

NSLog(@"Sorted: %@", sorted);

Предостережение: он не будет правильно обрабатывать юникодную букву, состоящую из десятичной цифры, как первый компонент, но я буду считать это патологическим случаем, пока кто-то не сможет меня просветить.

...