iOS开发之排序方法比较

在开发应用程序的时候,有时我们需要对一组无序的内容进行排序,iOS中有系统自带的方法来对NSAray进行排序,我们来对这些方法进行性能上的对比:

NSComparator排序

NSDescriptor排序

function排序

quickSort排序

由于排序的对象经常是自定义的,因此我们定义一个如下的对象:

@interface Topic : NSObject

@property (nonatomic, assign) NSInteger ID;
@property (nonatomic, copy) NSString *content;

@end

然后生成一个包含10000个对象的数组,对像的ID都是随机的:

NSMutableArray *unSortedArray = [NSMutableArray new];
for(NSInteger i = 0; i <10000;i++)
{
    Topic *topic = [Topic new];
     topic.ID = arc4random() % 10000;
     topic.content = [NSString stringWithFormat:@"This is :%@",[NSNumber  numberWithLong: topic.ID]];
    [unSortedArray addObject:topic];
}        

计算时间差的方法:

  CFAbsoluteTime start = CFAbsoluteTimeGetCurrent();
  CFAbsoluteTime end  = CFAbsoluteTimeGetCurrent();
  NSLog(@"time cost: %0.3f ms", (end - start)*1000);

使用NSComparator排序

comparator的定义如下所示:

typedef NSComparisonResult (^NSComparator)(id obj1, id obj2);

上面的参数(obj1、obj2)就是我们将要做比较的对象。block返回的结果为NSComparisonResult类型来表示两个对象的顺序。

对上述的无序array的对象ID进行排序,代码如下:

 NSArray *sortedArray = [unSortedArray sortedArrayUsingComparator:^(id obj1,id obj2){   NSInteger val1 = ((Topic*)obj1).ID;   NSInteger val2 = ((Topic*)obj2).ID;  //升序,假如需要降序的话,只需要修改下面的逻辑   if (val1 < val2)  {     return NSOrderedAscending;  }  else  {     return NSOrderedDescending;  }}

使用NSDescriptor排序

sort descriptor可以很方便的对数组进行多个key的排序。比如要对数组的对象先做ID排序,然后在对content进行排序的话,可以写成:

NSSortDescriptor *firstDescriptor = [[NSSortDescriptor alloc] initWithKey:@"ID" ascending:YES];
NSSortDescriptor *secondDescriptor = [[NSSortDescriptor alloc] initWithKey:@"content" ascending:YES];
NSArray *sortArray = [NSArray arrayWithObjects:firstDescriptor,secondDescriptor,nil];

NSArray  *sortedArray = [unSortedArray sortedArrayUsingDescriptors:sortArray];

使用函数排序

具体代码实现方式如下:

NSInteger customSort(id obj1, id obj2,void* context){   Topic *topic1 = (Topic*)obj1;
    Topic *topic2 = (Topic*)obj2;
    NSInteger val1 = topic1.ID;
    NSInteger val2 = topic2.ID;
    if (val1 > val2)   {
        return (NSComparisonResult)NSOrderedDescending;
    }
    if (val1 < val2)   {
        return (NSComparisonResult)NSOrderedAscending;
    }
    return (NSComparisonResult)NSOrderedSame;
}
 sortedArray = [array sortedArrayUsingFunction:customSort context:nil];

快速排序

快速排序我想大多数的人都听过,由于排序效率在同为O(N*logN)的几种排序方法中效率较高,因此我们也对比以一下快排的表现,下面是快排的代码:

void quickSort(NSMutableArray *array, NSInteger first, NSInteger last, NSComparator comparator) {
    if (first >= last) return;
    id pivot = array[(first + last) / 2];
    NSInteger left = first;
    NSInteger right = last;
    while (left <= right) {
        while (comparator(array[left], pivot) == NSOrderedAscending)
            left++;
        while (comparator(array[right], pivot) == NSOrderedDescending)
            right--;
        if (left <= right)
            [array exchangeObjectAtIndex:left++ withObjectAtIndex:right--];
    }
    quickSort(array, first, right, comparator);
    quickSort(array, left, last, comparator);
}

NSArray* sort(NSArray *unsorted, NSComparator comparator)
{
    NSMutableArray *a = [NSMutableArray arrayWithArray:unsorted];
    quickSort(a, 0, a.count - 1, comparator);return a;
}
  sortedArray = sort(array, ^(id obj1, id obj2)
                       {
                           Topic *topic1 = (Topic*)obj1;
                           Topic *topic2 = (Topic*)obj2;
                           NSNumber *val1 =[NSNumber numberWithLong:topic1.ID];
                           NSNumber *val2 = [NSNumber numberWithLong:topic2.ID];
                           return [val1 compare:val2];
                       });

结果对比

iPhone4:

2014-10-17 13:51:31.980 Algorithm_test[9578:907] NSComparator sort time cost: 163.708ms
2014-10-17 13:51:32.273 Algorithm_test[9578:907] NSSortDescriptor sort time cost: 291.293ms
2014-10-17 13:51:32.559 Algorithm_test[9578:907] function sort time cost: 281.485ms
2014-10-17 13:51:36.582 Algorithm_test[9578:907] quick sort time cost: 4013.582ms
iPhone5s:

2014-10-17 14:02:59.323 Algorithm_test[2971:60b] NSComparator sort time cost: 19.238ms
2014-10-17 14:02:59.348 Algorithm_test[2971:60b] NSSortDescriptor sort time cost: 24.183ms
2014-10-17 14:02:59.380 Algorithm_test[2971:60b] function sort time cost: 31.967ms
2014-10-17 14:02:59.468 Algorithm_test[2971:60b] quick sort time cost: 86.205ms

可以发现前3种系统自带的方法运行速度很快,即便是在4这种老机器排序10000个对象也不到1s的时间,可以看出苹果对算法的优化还是挺好的,但是快排的表现却不尽如人意,至于5s机器上,上述的排序时间都在几十毫秒,几乎可以忽略不计。因此建议在需要排序的时候采用系统自带的方法,至于用哪个可以看情况自己选择。

示例代码:https://github.com/FreeMind-LJ/HelloWrold/tree/master/Algorithm_test

时间: 2024-10-12 09:25:36

iOS开发之排序方法比较的相关文章

iOS开发——实用篇&amp;提高iOS开发效率的方法和工具

提高iOS开发效率的方法和工具 介绍 这篇文章主要是介绍一下我在iOS开发中使用到的一些可以提升开发效率的方法和工具. IDE 首先要说的肯定是IDE了,说到IDE,Xcode不能跑,当然你也可能同时在使用AppCode等其他的IDE,在这里我主要介绍Xcode中提升开发效率的方法. 1.善用快捷键 快捷键是开发中必不可少的,当你善于使用快捷键的时候,十指在键盘上飞舞,那画面太美,我不敢想象. 常用快捷键操作 2.常用代码片段 开发中有一些常用的代码,可以放到代码片段中,然后下次你就可以使用快捷

iOS开发 UITableView的方法和属性总结

本文描述UITableView的各种方法,属性,委托以及数据源.本文的目的只是总结UITableView的用法,详细的例子另撰文描述. 1 数据源  UITableViewDataSource协议 01 返回组(节)的个数,默认是返回1,如果只有1组数据,可以不用实现该方法. - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView 02 返回某一组的行数,该组由section的值决定 - (NSInteger)table

iOS开发隐藏键盘方法总结

iOS开发里键盘是经常需要打交道的地方,下面为大家带来我整理总结的几种隐藏键盘的方法. 一.隐藏自身软键盘 当对于有多个UITextField控件都想通过点击“Return”来隐藏自身软键盘的情况,这时的最好办法是使用Did End on Exit事件.在点击软键盘右下角的“Return”按钮后,会触发该事件.该事件有一个sender参数表示当前文本框,这样便可以编写一个通用的事件处理方法(.m文件). - (IBAction)TextField_DidEndOnExit:(id)sender 

&lt;转&gt;提高iOS开发效率的方法和工具

介绍 这篇文章主要是介绍一下我在iOS开发中使用到的一些可以提升开发效率的方法和工具. IDE 首先要说的肯定是IDE了,说到IDE,Xcode不能跑,当然你也可能同时在使用AppCode等其他的IDE,在这里我主要介绍Xcode中提升开发效率的方法. 1.善用快捷键 快捷键是开发中必不可少的,当你善于使用快捷键的时候,十指在键盘上飞舞,那画面太美,我不敢想象. 常用快捷键操作 2.常用代码片段 开发中有一些常用的代码,可以放到代码片段中,然后下次你就可以使用快捷方法来使用这些代码了,给大家看下

提高iOS开发效率的方法和工具

IDE 首先要说的肯定是IDE了,说到IDE,Xcode不能跑,当然你也可能同时在使用AppCode等其他的IDE,在这里我主要介绍Xcode中提升开发效率的方法. 1.善用快捷键 快捷键是开发中必不可少的,当你善于使用快捷键的时候,十指在键盘上飞舞,那画面太美,我不敢想象. 常用快捷键操作 2.常用代码片段 开发中有一些常用的代码,可以放到代码片段中,然后下次你就可以使用快捷方法来使用这些代码了,给大家看下我的Xcode中部分代码片段: 偷懒小技巧 3.Xcode插件 我想插件是Xcode必不

iOS开发——网络请求方法汇总

在实际的项目开发中,连接网络是每一款App必不可少的基本功能.对于客户端的网络请求而言,无非是有两个实现方向:使用网络请求框架或者不使用网络请求框架.在这篇博客中,我将用苹果自带的网络请求方式(不使用第三方框架)下对iOS网络请求方法做一个汇总.我将在之后的博客中介绍使用AFNetworking框架进行请求的实现.代码已经上传至:https://github.com/chenyufeng1991/iOS-NetworkRequest   . [使用XML请求Webservice,可用GET或PO

ios 开发 NSArray 排序

针对NSString字符串的排序 方法一: NSArray *ary = @[@"a3",@"a1",@"a2",@"a10",@"a24"]; NSLog(@"%@",ary); NSArray *myary = [ary sortedArrayUsingComparator:^(NSString * obj1, NSString * obj2){     return (NSComp

iOS开发:didSelectRowAtIndexPath:方法失效解决办法

问题描述及解决过程: 为了达到点击TableView空白区退出键盘的效果,给控制器注册了一个UITapGestureRecognizer来识别点击事件,代码如下: 1 #pragma mark - 设置手势识别器 2 3 - (void)setupGestureRecognizer 4 { 5 // 创建手势识别器对象 6 UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] init]; 7 // 设置手势识别器对象的代理为

iOS开发 非常全的三方库、插件、大牛博客等等

UI 下拉刷新 EGOTableViewPullRefresh- 最早的下拉刷新控件. SVPullToRefresh- 下拉刷新控件. MJRefresh- 仅需一行代码就可以为UITableView或者CollectionView加上下拉刷新或者上拉刷新功能.可以自定义上下拉刷新的文字说明.具体使用看"使用方法". (国人写) XHRefreshControl- XHRefreshControl 是一款高扩展性.低耦合度的下拉刷新.上提加载更多的组件.(国人写) CBStoreHo