欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

[iOS/OC] dispatch_apply性能分析

程序员文章站 2022-04-12 20:07:01
[iOS/OC] dispatch_apply性能分析。今天对dispatch_apply的性能进行了简单的分析,简单记录下。 dispatch_apply是GCD提供的,可以将...

[iOS/OC] dispatch_apply性能分析。今天对dispatch_apply的性能进行了简单的分析,简单记录下。
dispatch_apply是GCD提供的,可以将迭代器转变为并发任务。
假设我们有一个计算斐波那契数列的算法(这里特意使用了递归):

long fibonacci(long x)
{
    if (x <=1) {
        return 1;
    } else {
        return fibonacci(x-1) + fibonacci(x-2);
    }
}

我们有一个事情要做:计算第15个斐波那契数:

- (void) dosomething {
    fibonacci(15);
}

我们有一个任务要做:做50次的重复计算dosomething(),通常我们的做法是:

for (int i = 0; i

这个方法是串行的,会依次执行每次的单个计算,直至结束。如果我们需要并行计算,有一个比较简单的方法,就是使用dispatch_apply:

dispatch_queue_t queue = dispatch_get_global_queue(0, 0);
dispatch_apply(count, queue, ^(size_t index){
    [self dosomething];
});

那么,这里就会有一个利弊权衡了。什么时候用for循环进行串行操作,什么时候用dispatch_apply进行并行操作。当每次任务都是独立的时候,两种方案都可以用,这里我从性能的角度分析下两个方案。
dispatch_apply是一种多线程方案,将需要进行线程切换,线程同步等操作,会有一定的耗时,当单次任务执行的耗时较短,甚至小于线程切换的耗时时,显然使用for循环进行串行操作性能更优。

- (void)touch {
    NSInteger count = 50;
    // 1.dispatch
    NSTimeInterval date00,date01;
    date00 = [[NSDate date] timeIntervalSince1970];
    dispatch_queue_t queue = dispatch_get_global_queue(0, 0);
    dispatch_apply(count, queue, ^(size_t index){
        [self dosomething];
    });
    date01 = [[NSDate date] timeIntervalSince1970];

    // 2.for
    NSTimeInterval date10,date11;
    date10 = [[NSDate date] timeIntervalSince1970];
    for (int i = 0; i<count; i++)="" {="" [self="" dosomething];="" }="" date11="[[NSDate" date]="" timeintervalsince1970];="" printf("dispatch\t:="" %f\n",="" date01="" -="" date00);="" printf("for\t\t\t:="" date10);="" printf("------------------------------------------------------------------\n");="" 

此处,我使用时间戳对两个方案的耗时进行了统计。

设备:真机iTouch 6G
环境:singleView任务
结论:单次任务耗时10us为临界值;当单次任务耗时在10us以内时,串行操作性能更优,单次任务耗时在10us以上时,并行操作性能更优。

;>