zoukankan      html  css  js  c++  java
  • gcd 信号量

    • Block是编程语言层的特质,它允许你保存一段代码,在合适的使用取出来调用。如果对Block不够了解,请另查阅相关资料,本文章不对Block做解释。

    • Grand Central Dispatch简称(GCD)是Apple公司开发的技术,相比NSThread或NSOperation使用方便,并且优点是当处理器为多核时能利用多核的特征来创建线程。它首次发布在Mac OS X 10.6 ,iOS 4及以上也可用。

    • 我们知道GCD,但怎么在Block中使用它呢?答案是dispatch semaphore。需要了解信号量的createsignalwait

    1. dispatch_semaphore_create=> 创建一个信号量的初始值
    传入的参数为long,输出一个dispatch_semaphore_t类型且值为value的信号量。
    值得注意的是,这里的传入的参数value必须大于或等于0,否则dispatch_semaphore_create会返回NULL。

    2. dispatch_semaphore_signal=> 发送一个信号
    这个函数会使传入的信号量dsema的值加1。
    返回值为long类型,当返回值为0时表示当前并没有线程等待其处理的信号量,其处理的信号量的值加1即可。
    当返回值不为0时,表示其当前有(一个或多个)线程等待其处理的信号量,并且该函数唤醒了一个等待的线程(当线程有优先级时,唤醒优先级最高的线程;否则随机唤醒)。

    3. dispatch_semaphore_wait=> 等待一个信号
    这个函数会使传入的信号量dsema的值减1;
    如果dsema信号量的值大于0,该函数所处线程就继续执行下面的语句,并且将信号量的值减1;
    如果desema的值为0,那么这个函数就阻塞当前线程等待timeout(注意timeout的类型为dispatch_time_t,
    不能直接传入整形或float型数),如果等待的期间desema的值被dispatch_semaphore_signal函数加1了,
    且该函数(即dispatch_semaphore_wait)所处线程获得了信号量,那么就继续向下执行并将信号量减1。
    如果等待期间没有获取到信号量或者信号量的值一直为0,那么等到timeout时,其所处线程自动执行其后语句。

    4. timeout
    在设置timeout时,比较有用的两个宏:
    DISPATCH_TIME_NOW     表示当前;
    DISPATCH_TIME_FOREVER   表示未来;
    一般可以直接设置timeout为这两个宏其中的一个,或者自己创建一个dispatch_time_t类型的变量。
    创建dispatch_time_t类型的变量有两种方法,dispatch_time和dispatch_walltime。
    利用创建dispatch_time创建dispatch_time_t类型变量的时候一般也会用到这两个变量。
    dispatch_time的声明如下:
    dispatch_time_t dispatch_time(dispatch_time_t when, int64_t delta);
    其参数when需传入一个dispatch_time_t类型的变量,和一个delta值。表示when加delta时间就是timeout的时间。
    例如:
    dispatch_time_t t = dispatch_time(DISPATCH_TIME_NOW, 110001000*1000);
    表示当前时间向后延时一秒为timeout的时间。

    • 现在我们使用dispatch semaphore去实现等待Block操作结束。
    • 单个Block:
    dispatch_semaphore_t sem = dispatch_semaphore_create(0);      
    [self methodWithABlock:^(id result){
          //写block中做的事情
          //结束等待
          dispatch_semaphore_signal(sem);
    }];
    //等待信号
    dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER);
    
    • 多个Block:
    dispatch_semaphore_t sem = dispatch_semaphore_create(0);
    [self methodWithABlock:^(id result){
          //写block中做的事情
          dispatch_semaphore_signal(sem);
    }];
    [self methodWithABlock:^(id result){
          //写block中做的事情
          dispatch_semaphore_signal(sem);
    }];
    dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER);
    dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER);
    
    • Block中的Block
    dispatch_semaphore_t sem = dispatch_semaphore_create(0);
    [self methodWithABlock:^(id result){
          //写block中做的事情
          dispatch_semaphore_signal(sem);
          [self methodWithABlock:^(id result){
              //写block中做的事情
              dispatch_semaphore_signal(sem);
          }];
    }];
    dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER);
    dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER);
  • 相关阅读:
    Lambda表达式、依赖倒置
    ASP.NET vNext 概述
    Uname
    RHEL4 i386下安装rdesktop【原创】
    Taxonomy of class loader problems encountered when using Jakarta Commons Logging(转)
    How to decompile class file in Java and Eclipse
    先有的资源,能看的速度看,不能看的,抽时间看。说不定那天就真的打不开了(转)
    Google App Engine 学习和实践
    【VBA研究】VBA通过HTTP协议实现邮件轨迹跟踪查询
    js正則表達式语法
  • 原文地址:https://www.cnblogs.com/xukuangbo/p/9518123.html
Copyright © 2011-2022 走看看