【问题标题】:Sorting an NSMutableArray containing matching "pairs" of values对包含匹配“对”值的 NSMutableArray 进行排序
【发布时间】:2010-10-04 00:21:50
【问题描述】:

我不希望改变 anArray 的设计方式,因为它也在其他地方用作 UITableView 的数据源。奇数值是“用户名”,偶数值是它们匹配的“日期”。 (“对”必须保持在一起。)

如何“按用户名”排序?

如何“按日期”排序?

我应该使用 sortUsingFunction 还是 sortUsingSelector?

-(void) test
{
    NSMutableArray *anArray = [NSMutableArray arrayWithObjects:@"Zeke", @"01-Jan-2010", @"Bob", @"02-Jan-2010", @"Fred", @"03-Jan-2010", @"Susan", @"04-Jan-2010", @"Kim", @"05-Jan-2010", @"Debbie", @"06-Jan-2010", nil];
    [anArray sortUsingFunction:SortByDate context:(void *)context];
}

NSComparisonResult SortByDate(NSMutableArray *a1, NSMutableArray *a2, void *context) 
{
   // What goes here to keep the pair-values "together"?
}

【问题讨论】:

    标签: iphone objective-c sorting methods nsmutablearray


    【解决方案1】:

    你为什么不使用 NSDictionary?您可以将用户名作为键,将日期作为相应的值。然后,如果您想对用户名进行排序,只需使用 [dictObj allkeys] 即可获取仅包含键的数组。根据您的喜好对它们进行排序,然后在显示时显示排序的键数组并获取键的相应值并在旁边显示。同样,您可以使用 [dictObj allValues] 对它们进行排序并与键一起显示它们。

    【讨论】:

    • 呃。这涉及到使用 -[NSDictionary allKeysForObject:] 不能很快。
    • 当排序键(例如上面的日期)不能保证对每个对象都是唯一的时,这种方法将不起作用。
    【解决方案2】:

    我不想改变 anArray 的设计方式,因为它也在其他地方用作 UITableView 的数据源

    这是否意味着单元格在显示用户名和日期之间交替显示,或者您是在乘以/除以 2?

    无论哪种方式,您都需要修复模型。你去“哎呀,排序不起作用”的那一点应该是一个很大的暗示,你没有选择一个好的数据表示。添加解决方法只会在以后导致更多的眼泪。

    我建议这样:

    1. 创建一个类来表示您的(用户名,日期)元组。
    2. 添加 -compareByDate: 和 -compareByUsername: 方法。
    3. [数组 sortUsingSelector:@selector(compareByDate:)]

    如果您想在交替的单元格中显示用户名和日期,那么这仍然很容易,但我只需使用更高的单元格并为自己省点麻烦。

    注意: Objective-C 方法调用的开销意味着您可以通过使用 sortUsingComparator: 并定义适当的函数来获得显着的性能提升(您可以将函数粘贴在 @implmentation 和 @end 之间让他们访问受保护的/私有的 ivars),但除非您确定排序是一个瓶颈,否则这样做并不值得。

    【讨论】:

    • 不幸的是,不可能为我们多年前继承的这个烂摊子添加更多的类、更多的代码、更多的复杂性。我无法再进行一次对话,试图说服其他城市的其他部门重新设计他们的代码……这样我们才能以“正确”的方式“对 7 个项目进行排序并节省 0.001 秒的时间”。真的没有办法“在现有的 NSArray 设计中成对排序项目”吗? (如果我告诉他们“这完全不可能”......我相信这也会造成重大问题。)
    • 哦,那种的代码。对不起☹我只是将它们包装在类中,对它们进行排序,然后再次打开它们。
    • 但是如何将它们包装在类中,对它们进行排序,然后再次打开它们?
    【解决方案3】:

    这样的事情可能会奏效:

    @class SortWrapper: NSObject
    @property (copy,readwrite,atomic) NSString* name;
    @property (copy,readwrite,atomic) NSDate* date;
    @end
    
    ...
    
    - (void)test
    {
        NSArray* names = @[@"Alice", @"Bob", @"Cameron"];
        NSArray* dates = @[aliceDOB, bobDOB, cameronDOB]; // NSDate objects
    
        // turn into wrapped objects for sorting    
        NSMutableArray* wrappedObjects = [NSMutableArray array];
        for ( int i=0; i<names.count; i++ ) {
            SortWrapper* wrapped = [[SortWrapper alloc] init];
            wrapped.name = names[i];
            wrapped.date = dates[i];
            [wrappedObjects addObject:wrapped];
        }
    
        // to sort by date:
        NSArray* sortedByDate = [wrappedObjects sortedArrayUsingComparator:^NSComparisonResult(SortWrapper* obj1, SortWrapper* obj2) {
            return [obj1.date compare:obj2.date];
        }];
    
        // to sort by name:
        NSArray* sortedByName = [wrappedObjects sortedArrayUsingComparator:^NSComparisonResult(SortWrapper* obj1, SortWrapper* obj2) {
            return [obj1.name compare:obj2.name];
        }];
    
    }   
    

    【讨论】:

      猜你喜欢
      • 2013-11-08
      • 2015-08-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-22
      • 1970-01-01
      相关资源
      最近更新 更多