iOS 多线程之GCD实例

  1. 一个接口的请求,依赖于另一个请求的结果
  • 使用GCD组队列中的dispatch_group_async和dispatch_group_notify
arduino 复制代码
- (void)dispatchGroup{
    dispatch_queue_t queue = dispatch_queue_create("com.test", DISPATCH_QUEUE_CONCURRENT);
    dispatch_group_t group = dispatch_group_create();
    dispatch_group_async(group, queue, ^{
        // 请求1
        NSLog(@"11111");
    });
    
    dispatch_group_notify(group, queue, ^{
        // 请求2
        NSLog(@"2222222");
    });
}
  • 使用GCD的栅栏函数dispatch_barrier_async
arduino 复制代码
- (void)dispatchBarrier{
    dispatch_queue_t queue = dispatch_queue_create("com.test", DISPATCH_QUEUE_CONCURRENT);
    dispatch_async(queue, ^{
        // 请求1
        NSLog(@"11111");
    });
    
    dispatch_barrier_async(queue, ^{
        // 请求2
        NSLog(@"22222");
    });
}
  • 使用GCD的信号量dispatch_semaphore,信号量的初始值可以用来控制线程并发访问的最大数量。如果设置为1则为串行执行,达到线程同步的目的
scss 复制代码
- (void)dispatchSemaphore{
    dispatch_queue_t queue = dispatch_queue_create("com.test", DISPATCH_QUEUE_CONCURRENT);
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
    
    dispatch_async(queue, ^{
        NSLog(@"11111");
        // 请求1结束后 增加信号个数,dispatch_semaphore_signal()信号加1
        dispatch_semaphore_signal(semaphore);
    });
    
    dispatch_async(queue, ^{
        // 无限等待,直到请求1结束 增加了信号量,大于0后才开始,dispatch_semaphore_wait()信号减1
        // 如果信号量的值 > 0,就让信号量的值减1,然后继续往下执行代码
        // 如果信号量的值 <= 0,就会休眠等待,直到信号量的值变成>0,就让信号量的值减1,然后继续往下执行代码
        // DISPATCH_TIME_FOREVER 这个是一直等待的意思
        dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
        // 请求2开始
        NSLog(@"22222");
    });
}
  1. 在异步线程中return一个字符串
  • 模拟异步线程方法,需要return字符串@"小熊"
scss 复制代码
- (void)asyncRequestMethod:(void(^)(NSString *name))successBlock{
    dispatch_queue_t queue = dispatch_queue_create("com.test", DISPATCH_QUEUE_SERIAL);
    dispatch_async(queue, ^{
        if (successBlock) {
            successBlock(@"小熊");
        }
    });
}
  • while循环等待阻塞线程方法
objectivec 复制代码
- (NSString *)nameStr{
    __block NSString *nameStr = @"小关";
    __block BOOL isSleep = YES;

    [self asyncRequestMethod:^(NSString *name) {
        nameStr = name;
        NSLog(@"1");
        isSleep = NO;
        NSLog(@"3");
    }];

    //while循环等待阻塞线程
    while (isSleep) {
        NSLog(@"4");
    }

    NSLog(@"2");

    return nameStr;
}
  • 用信号量控制,异步改同步
ini 复制代码
- (NSString *)nameStr{
    __block NSString *nameStr = @"小关";
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);

    [self asyncRequestMethod:^(NSString *name) {
        nameStr = name;
        dispatch_semaphore_signal(semaphore);
    }];

    dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);

    return nameStr;
}
  • 利用dispatch_group_t调度组,异步改同步
ini 复制代码
- (NSString *)nameStr{
    __block NSString *nameStr = @"小关";
    dispatch_group_t group = dispatch_group_create();
    dispatch_group_enter(group);

    [self asyncRequestMethod:^(NSString *name) {
        nameStr = name;
        dispatch_group_leave(group);
    }];

    dispatch_group_wait(group, DISPATCH_TIME_FOREVER);

    return nameStr;
}

附:GrandCentralDispatchDemo

相关推荐
梦曦i24 分钟前
uni-storage 0.1.0 发布:TTL过期管理+多实例隔离
前端·storage·uni-app x
黑科技iOS上架1 小时前
App Store5.6隐藏功能究竟怎么排查?
ios·审核
猫头_1 小时前
AI 流式传输工程指南:模型吐出半截 JSON,前端如何边收边渲染?
前端·javascript·llm
console.log('npc')2 小时前
第 1 章 项目概述与环境搭建
前端·人工智能·大模型
定栓2 小时前
Webpack迁到Vite第七节(二):全家桶移除 — Babel 全家桶深度分析
前端·webpack·node.js
IT_陈寒2 小时前
React组件莫名重渲染?你可能忘了这个小细节
前端·人工智能·后端
鶴哥只手遮天2 小时前
React 19.3.1 源码深度剖析-第 12 章(下)RSC 与 Flight 协议
前端·react.js·开源
deli0072 小时前
TCP 三次握手到底发几个包?丢包重传动画实测一遍
前端
盟接之桥2 小时前
盟接之桥谈线束数字化-按单入按单出:线束企业库存管理的破局之道
大数据·前端·网络·数据库·人工智能·制造
巴勒个啦2 小时前
Prompt Engineering 实战:5 个让 AI 生成生产级业务代码的工程模式
java·前端