GCD-Barrier

来源:互联网 发布:虚拟拍照软件下载 编辑:程序博客网 时间:2024/06/08 19:35

[TOC]
Barrier: n. (用来禁止通行的各种)障碍物(如: 栅栏和关卡)

在看GCD的barrier如何使用前,我们先了解barrier的英文意思.
barrier的用法非常简单,这里我就不过多赘述,且看下面的代码:

- (void)barrier{    dispatch_queue_t queue = dispatch_queue_create("com.example.gcd.for", DISPATCH_QUEUE_CONCURRENT);    NSMutableArray *arr = @[].mutableCopy;    [arr addObject:@(1)];    dispatch_async(queue, ^{        NSLog(@"bl1 arr: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl2 arr: %@", arr);    });    dispatch_async(queue, ^{        [arr addObject:@(0)];        [NSThread sleepForTimeInterval:2.0];        [arr addObject:@(7)];        NSLog(@"finished: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl4 arr: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl5 arr: %@", arr);    });    dispatch_async(queue, ^{        [NSThread sleepForTimeInterval:2.5];        NSLog(@"bl6 arr: %@", arr);    });}/*输出:2016-12-29 17:53:10.681 GCD-Barrier[33828:1500632] bl2 arr: (    1)2016-12-29 17:53:10.681 GCD-Barrier[33828:1500627] bl1 arr: (    1)2016-12-29 17:53:10.681 GCD-Barrier[33828:1500646] bl4 arr: (    1,    0)2016-12-29 17:53:10.681 GCD-Barrier[33828:1500632] bl5 arr: (    1,    0)2016-12-29 17:53:12.754 GCD-Barrier[33828:1500647] finished: (    1,    0,    7)2016-12-29 17:53:13.229 GCD-Barrier[33828:1500654] bl6 arr: (    1,    0,    7)*/

上面这段代码模拟了一个异步读写操作. bl1bl2读取到的结果都是1,而bl4bl5读取到的结果是1,0,我在bl2bl4之间插入了一个写入操作,第一个是一个没有延迟的写入操作,然后模拟了延迟2.5秒的一个写入操作,插入了一个7,结果是只有加了延迟的bl6的读取操作是正确的.
为什么这样说,因为在同一时间,不同的用户进行了不同的操作,比如评论,当我看别人的评论的时候,恰巧有个人刚提交了一个评论,提交评论时,需要执行一个插入操作,但是这时我读取到的评论列表没有那个人刚刚提交的评论,这样有可能会造成某种误会.
所以我们需要用些手段,当有写入操作的时候,不能让别的线程来进行读取,等写入完毕后,再允许别的线程读取.
GCD很方便的为我们提供了这种功能,且看下面这段代码:

- (void)barrier{    dispatch_queue_t queue = dispatch_queue_create("com.example.gcd.for", DISPATCH_QUEUE_CONCURRENT);    NSMutableArray *arr = @[].mutableCopy;    [arr addObject:@(1)];    dispatch_async(queue, ^{        NSLog(@"bl1 arr: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl2 arr: %@", arr);    });    dispatch_barrier_async(queue, ^{        [arr addObject:@(0)];        [NSThread sleepForTimeInterval:2.0];        [arr addObject:@(7)];        NSLog(@"finished: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl4 arr: %@", arr);    });    dispatch_async(queue, ^{        NSLog(@"bl5 arr: %@", arr);    });    dispatch_async(queue, ^{        [NSThread sleepForTimeInterval:2.5];        NSLog(@"bl6 arr: %@", arr);    });}/**输出结果:2016-12-30 09:40:01.353 GCD-Barrier[35219:1890287] bl1 arr: (    1)2016-12-30 09:40:01.353 GCD-Barrier[35219:1890761] bl2 arr: (    1)2016-12-30 09:40:03.385 GCD-Barrier[35219:1890761] finished: (    1,    0,    7)2016-12-30 09:40:03.385 GCD-Barrier[35219:1890287] bl5 arr: (    1,    0,    7)2016-12-30 09:40:03.385 GCD-Barrier[35219:1890761] bl4 arr: (    1,    0,    7)2016-12-30 09:40:05.924 GCD-Barrier[35219:1890762] bl6 arr: (    1,    0,    7)*/

上面的代码,我们使用了dispatch_barrier_async这个方法,这个方法里面的任务执行的时候,会挂起当前队列里其他的任务,当这个方法里的任务执行完成之后,别的任务再继续执行.如下图:
dispatch_barrier_async
嗯..就酱.
联系方式: 958246321

0 0
原创粉丝点击