考察点:
- 并发队列 + 异步栅栏dispatch_barrier_async()
- 线程安全
- 关于资源竞争的处理
- 基于线程安全的多读单写的处理,读的操作需要立马返回结果的,所以,在读数据操作,使用同步提交任务到并发队列中
例子1:字典安全处理
在多线程编程中,最常见的场景是如何保证线程安全,比如你可能经常遇到多线程访问某个dic(又或者是array或其他)造成的crash。如何使用GCD实现多线程读者与写者问题,也即单一资源的线程安全问题。
_ioQueue = dispatch_queue_create("ioQueue", DISPATCH_QUEUE_CONCURRENT);- (void)setSafeObject:(id)object forKey:(NSString *)key {key = [key copy];dispatch_barrier_async(self.ioQueue, ^{if (key && object) {[_dic setObject:object forKey:key];}});}- (id)getSafeObjectForKey:(NSString *)key {__block id result = nil;dispatch_sync(self.ioQueue, ^{result = [_dic objectForKey:key];});return result;}
例子2、多读单写解决思
读取处理是可以并发的,但是写入处理却是不允许并发执行的。
- (void)dispatch_barrier_test{dispatch_queue_t meetingQueue = dispatch_queue_create("com.meeting.queue", DISPATCH_QUEUE_CONCURRENT);dispatch_async(meetingQueue, ^{NSLog(@"读取操作1"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作2"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作3"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作4"); });dispatch_barrier_async(meetingQueue, ^{NSLog(@"写入操作"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作"); });dispatch_async(meetingQueue, ^{NSLog(@"读取操作"); });}

