• ios学习:多线程二(GCD初步介绍)


    xib文件就放了四个button和四个label

     1 //
     2 //  TWFXViewController.h
     3 //  Demo_GCD
     4 //
     5 //  Created by Lion User on 12-12-11.
     6 //  Copyright (c) 2012年 Lion User. All rights reserved.
     7 //
     8 
     9 #import <UIKit/UIKit.h>
    10 
    11 @interface TWFXViewController : UIViewController
    12 
    13 @property (retain, nonatomic) IBOutlet UILabel *outletLabel1;
    14 @property (retain, nonatomic) IBOutlet UILabel *outletLabel2;
    15 @property (retain, nonatomic) IBOutlet UILabel *outletLabel3;
    16 @property (retain, nonatomic) IBOutlet UILabel *outletLabel4;
    17 
    18 - (IBAction)btnClick4:(UIButton *)sender;
    19 - (IBAction)btnClick2:(UIButton *)sender;
    20 - (IBAction)btnClick3:(UIButton *)sender;
    21 - (IBAction)btnClick:(UIButton *)sender;
    22 @end
      1 //
      2 //  TWFXViewController.m
      3 //  Demo_GCD
      4 //
      5 //  Created by Lion User on 12-12-11.
      6 //  Copyright (c) 2012年 Lion User. All rights reserved.
      7 //
      8 /*
      9  GCD(系统管理线程) 简介
     10  使用GCD你不需要编写线程代码,只需定义想要执行的任务,然后添加到适当的 dispatch queue (调度队列)里
     11  GCD会负责创建线程和调度你的任务.系统直接提供线程管理,比应用实现更高效
     12  
     13  基于C的执行自定义任务机制,dispatch queue 按先进先出的顺序,串行或并发地执行任务.dispatch queue 分以下三种:
     14  serial dispatch queue : 串行调度队列,一次只执行一个任务,直到当前任务完成才开始出列并启动下一个任务
     15                          主要用于对特定资源的同步访问.虽然每个串行queue本身每次只能执行一个任务,但各个串行queue之间是并发执行的
     16  concurrent dispatch queue: 也称为 global dispatch queue, 并行调度队列,并发执行一个或多个任务,但启动顺序仍是按照添加到queue的顺序启动
     17                             你不能创建并发dispatch queues, 只能使用系统已经定义好了的三个全局并发queues,具体下面说到
     18  main dispatch queue : 全局可用的串行 queue,在应用主线程中执行任务,比如用于刷新UI界面
     19  
     20  
     21  dispatch queue 相关的技术
     22  Dispatch group : 用于监控一组block对象完成
     23  Dispatch semaphore : 类似于传统的 semaphore (信号量)
     24  Dispatch Source : 系统事件异步处理机制
     25  
     26  dispatch queue 中的 各个线程,可以通过queue的context指针来共享数据
     27  
     28  */
     29 
     30 
     31 #import "TWFXViewController.h"
     32 
     33 @interface TWFXViewController ()
     34 
     35 @end
     36 
     37 @implementation TWFXViewController
     38 
     39 - (void)viewDidLoad
     40 {
     41     [super viewDidLoad];
     42     // Do any additional setup after loading the view, typically from a nib.
     43 }
     44 
     45 - (void)didReceiveMemoryWarning
     46 {
     47     [super didReceiveMemoryWarning];
     48     // Dispose of any resources that can be recreated.
     49 }
     50 
     51 
     52 /*
     53  全局并发 Dispatch queue
     54  1. 并发 dispatch queue 可以同时并发执行多个任务,不过并发 queue 仍然按照先进先出的顺序启动任务
     55  2. 并发 queue 同时执行的任务数量会根据应用和系统动态变化,各个因素如:可用核数量  其他进程正在执行的工作数量 其他串行dispatch queue 中的优先任务的数量等
     56  3. 系统会给每个应用程序提供三个并发 dispatch queue,全局共享,三个queue的唯一区别在于优先级不同 
     57  */
     58 - (IBAction)btnClick4:(UIButton *)sender {
     59     
     60     /*
     61      获取全局并发 dispatch queue : dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
     62      第一个参数表示 queue 的优先级,这里获取默认优先级的那个queue,也可以获取高/低优先级的那个,把 DEFAULT 换成 HIGH 或 LOW 就行了
     63      第二个参数表示 ?
     64      */
     65     dispatch_queue_t aQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
     66     
     67     
     68     //把一个block加入到全局并发调度队列里
     69     dispatch_async(aQueue, ^(void) {
     70                 
     71         for (int i = 0; i < 1000; i++) {
     72             
     73             //把block同步添加到主线程里,这样子,demo queue 就会暂停等这个block执行完成才继续执行
     74             dispatch_sync(dispatch_get_main_queue(), ^(void) {
     75                 
     76                 NSString *text = [NSString stringWithFormat:@"%d", i];
     77                 self.outletLabel3.text = text;
     78             });            
     79         }
     80         
     81     });
     82     
     83     
     84     //把另一个block加入到全局并发调度队列里.这个block和上面那个block会并发执行
     85     dispatch_async(aQueue, ^(void){
     86         
     87         for (int i = 0; i < 1000; i++) {
     88             
     89             //把block同步添加到主线程里,这样子,demo queue 就会暂停等这个block执行完成才继续执行
     90             dispatch_sync(dispatch_get_main_queue(), ^(void) {
     91                 
     92                 NSString *text = [NSString stringWithFormat:@"%d", i];
     93                 self.outletLabel4.text = text;
     94             });
     95         }
     96         
     97     });
     98     
     99 }
    100 
    101 
    102 /*
    103  串行 Dispatch queue
    104  1. 串行 queue 每次只能执行一个任务,可以使用它来代替锁,保护共享资源或可变的数据结构,串行queue确保任务按可预测的顺序执行(这是比锁好的地方)
    105  2. 必须显式创建和管理所有你使用的串行queue(数目任意)
    106  */
    107 - (IBAction)btnClick2:(UIButton *)sender {
    108     
    109     /*
    110      使用 dispatch_queue_create() 方法来创建串行queue
    111      第一个参数表示 queue 的名字, 第二个参数表示 queue 的一组属性(保留给将来使用)
    112      */
    113     dispatch_queue_t queue = dispatch_queue_create("demo queue", NULL);
    114     
    115     
    116     /*
    117      异步调度和同步调度
    118      异步调度 dispatch_async : 把一个任务添加到某queue后就马上离开,而不管任务在那个queue里的执行状态
    119      同步调度 dispatch_sync : 把一个任务添加到某queue后,等这个任务完成,调用线程才继续执行.尼玛,坑爹啊
    120      
    121      所以,异步调度和同步调度的区别不在于被添加的任务怎样执行,而在于调用线程是否等待任务执行完
    122      */
    123     
    124     //把block异步添加到上面创建的名为 demo queue 的调度队列里
    125     dispatch_async(queue, ^(void){
    126         
    127         for (int i = 0; i < 1000; i++) {
    128 
    129          //   sleep(1);
    130           //  printf("a%d\t",i);
    131             
    132             //把block同步添加到主线程里,这样子,demo queue 就会暂停等这个block执行完成才继续执行
    133             dispatch_sync(dispatch_get_main_queue(), ^(void) {
    134 
    135                 NSString *text = [NSString stringWithFormat:@"%d", i];
    136                 self.outletLabel1.text = text;
    137                // printf("b%d\n",i);
    138             });
    139             
    140         }
    141         
    142     });
    143     
    144     
    145     //因为 demo queue 是串行调度队列,所以等上面那个block执行完,下面这个block才会开始
    146     dispatch_async(queue, ^(void){
    147         
    148         for (int i = 0; i < 1000; i++) {
    149   
    150             dispatch_sync(dispatch_get_main_queue(), ^(void) {
    151                 
    152                 self.outletLabel2.text = [NSString stringWithFormat:@"%d", i];
    153                 
    154             });
    155         }
    156         
    157 
    158     });
    159     
    160     
    161     //xxxxx_create 的object对象要对应 xxxxx_release ?
    162     dispatch_release(queue);
    163 
    164     //这个循环都会卡屏幕~~~
    165 //    for (int i = 0; i < 100000; i++) {
    166 //        self.outletLabel1.text = [NSString stringWithFormat:@"%d", i];
    167 //        printf("%d\n", i);
    168 //    }
    169     
    170 }
    171 
    172              
    173 -(void)test:(NSString *)data
    174 {
    175     self.outletLabel1.text = data;
    176 }
    177 
    178 
    179 
    180 /*
    181  dispatch_group 可以把一组task放到一个group里,等group里的所有task都执行完后再继续运行
    182  */
    183 - (IBAction)btnClick3:(UIButton *)sender {
    184     
    185     //重置label2的text
    186     self.outletLabel2.text = @"begin";
    187     
    188     //获取一个全局并发 调度队列
    189     dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    190 
    191     //创建一个 dispatch group
    192     dispatch_group_t group = dispatch_group_create();
    193     
    194     //定义 task1
    195     dispatch_block_t task1 = ^(void){
    196         
    197         for (int i = 0; i < 300; i++) {
    198             
    199             dispatch_sync(dispatch_get_main_queue(), ^(void){
    200                 
    201                 self.outletLabel3.text = [NSString stringWithFormat:@"%d", i];
    202             });
    203         }
    204 
    205     };
    206     
    207     //定义task2
    208     dispatch_block_t task2 = ^(void){
    209         
    210         for (int i = 0; i < 300; i++) {
    211             
    212             dispatch_sync(dispatch_get_main_queue(), ^(void){
    213                 
    214                 self.outletLabel4.text = [NSString stringWithFormat:@"%d", i];
    215             });
    216         }
    217         
    218     };
    219     
    220     //把task1关联到 queue 和group
    221     dispatch_group_async(group, queue, task1);
    222     
    223     //把task2关联到 queue和group
    224     dispatch_group_async(group, queue, task2);
    225     
    226     
    227     //等group里的task都执行完后执行notify方法里的内容,相当于把wait方法及之后要执行的代码合到一起了
    228     dispatch_group_notify(group, dispatch_get_main_queue(), ^(void){
    229         
    230         self.outletLabel2.text = @"done!";
    231         
    232     });
    233     
    234     //XXX_create创建,就需要对应的 XXX_release()
    235     dispatch_release(group);
    236 }
    237 
    238 
    239 
    240 /*
    241  dispatch source
    242  */
    243 - (IBAction)btnClick:(UIButton *)sender {
    244 }
    245 
    246 
    247 - (void)dealloc {
    248     [_outletLabel1 release];
    249     [_outletLabel2 release];
    250     [_outletLabel3 release];
    251     [_outletLabel4 release];
    252     [super dealloc];
    253 }
    254 @end
  • 相关阅读:
    Postfix邮件服务器搭建及配置
    利用linux漏洞进行提权
    NFS部署和优化
    LAMP环境搭建
    Apache2.4.6服务器安装及配置
    linux笔记_防止ddos攻击
    CentOS6.5恢复误删除的文件
    linux计划任务
    linux软连接和硬链接
    linux用户和用户组的基本操作
  • 原文地址:https://www.cnblogs.com/zouzf/p/2816691.html
Copyright © 2020-2023  润新知