誰も解決策を提示できないようだから、思いついた解決策を投稿すると思った。まず、私は私のデータのためのモデルを作成しました:
@interface MyModel : NSObject
{
NSString* _value;
NSString* _sortableValue;
}
@property (nonatomic,copy) NSString* value;
- (NSString*)sortableValue;
- (NSString*)comparableString:(NSString*)str;
@end
彼らのモデルの鍵はsortableValueを作成するために使用されますcomparableString方法、です。
@implementation MyModel
@synthesize value=_value;
-(void)dealloc
{
[_value release];
[_sortableValue release];
[super dealloc];
}
- (void)setValue:(NSString*)value
{
[_value release];
_value = [value copy];
[_sortableValue release];
_sortableTValue = nil;
}
- (NSString*)sortableValue
{
if (_sortableValue == nil)
_sortableValue = [[self comparableString:_value] retain];
return _sortableValue;
}
- (NSString*)comparableString:(NSString*)str
{
if (str == nil)
return nil;
else if ([str length] == 0)
return [NSString stringWithString:str];
NSCharacterSet* numbersSet = [NSCharacterSet decimalDigitCharacterSet];
if ([str rangeOfCharacterFromSet:numbersSet options:0 range:NSMakeRange(0, 1)].location != NSNotFound)
return [NSString stringWithString:str];
NSRange range = NSMakeRange(0, [str length]);
if ([str compare:@"a " options:(NSAnchoredSearch|NSCaseInsensitiveSearch) range:NSMakeRange(0, 2)] == NSOrderedSame)
range.location = 2;
else if ([str compare:@"an " options:(NSAnchoredSearch|NSCaseInsensitiveSearch) range:NSMakeRange(0, 3)] == NSOrderedSame)
range.location = 3;
else if ([str compare:@"the " options:(NSAnchoredSearch|NSCaseInsensitiveSearch) range:NSMakeRange(0, 4)] == NSOrderedSame)
range.location = 4;
range.length -= range.location;
NSCharacterSet* lettersSet = [NSCharacterSet letterCharacterSet];
NSUInteger letterOffset = [str rangeOfCharacterFromSet:lettersSet options:0 range:range].location;
if (letterOffset == NSNotFound)
return [NSString stringWithString:str];
letterOffset -= range.location;
range.location += letterOffset;
range.length -= letterOffset;
return [str substringWithRange:range];
}
@end
文字列から先頭の記事を削除するだけでなく、主要な非文字文字も削除します。 iPodのライブラリに "$ ell Your $ oul"という曲があります。これはMPMediaPickerControllerのEセクションで終わります。最初のソートアルゴリズムを作成していたのではないかとは思いませんが、MPMediaPickerControllerとの整合性が保たれるようになりました。
パズルの最後の部分は、UILocalizedIndexedCollationクラスです。この便利な小さなヘルパークラスは、データをソートして、UITableViewDataSource経由でUITableViewに供給するようにします。ここではモデルと一緒にUILocalizedIndexedCollationクラスの使用方法の抜粋です:(Appleのドキュメントから)UILocalizedIndexedCollationについて
// tableData will contain an NSArray for each populated section in the table view
NSMutableDictionary* tableData = [NSMutableDictionary dictionary];
NSMutableArray* myArray = [NSMutableArray array];
// Populate myArray with instances of MyModel
UILocalizedIndexedCollation* indexer = [UILocalizedIndexedCollation currentCollation];
for (MyModel* data in myArray)
{
NSInteger index = [indexer sectionForObject:data collationStringSelector:@selector(sortableValue)];
NSNumber* key = [[NSNumber alloc] initWithInteger:index];
NSMutableArray* array = [tableData objectForKey:key];
if (array == nil)
{
array = [NSMutableArray new]; // Will be released after creating a sorted array in the following section
[tableData setObject:array forKey:key];
}
[array addObject:data];
[key release];
}
[tableData enumerateKeysAndObjectsUsingBlock:^(id key, id array, BOOL* stop)
{
NSMutableArray* sortedArray = [[indexer sortedArrayFromArray:array collationStringSelector:@selector(sortableValue)] mutableCopy];
[tableData setObject:sortedArray forKey:key];
[array release];
}];
一つの簡単なメモ:
アプリケーションが のLocalizable.stringsファイルを提供している場合 現在の言語設定の場合、 インデックス付き照合オブジェクトは、 メソッドによって返された各文字列をセレクタによって識別された によってローカライズします。
したがって、サポートする言語ごとにLocalizable.stringsを指定する必要があります。そうしないと、テーブルビューにセクションA-Zと#のみが表示されます。
これについての詳細をすべて解説するにはしばらく時間がかかりました。だから、他の人にとって役に立つと思っています。私がこれを改善できる方法があれば、教えてください!
+1素晴らしい仕事の男。私は一度ウルクを見たことがありますが、解決策を見つけ出す時間はありません。よくやった。 – KingofBliss
恐ろしい答え。おそらく、私は 'MPMediaQuery'でこれを実装する方法を提案できますか?これを 'UITableViewController'クラスにどのように含めると、セクションの文字のリストで別の配列を作る必要がありますか? – sooper