多线程

#import "ViewController.h"
#import "MyNSOperation.h"

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    /*
     程序:由源代码生成的可执行应用.(例如:QQ.app)
     进程:一个正在运行的程序可以看做一个进程.(例如正在运行的qq就是一个进程),进程拥有独立运行所需的全部资源.
     线程:程序中独立运行的代码段.(例如:接收QQ消息的代码)
     一个进程是由一个或者多个线程组成.进程只负责资源的调度和分配,线程才是真正的执行单元,负责代码的执行
     */
    /*
     单线程
     每个正在运行的程序(即进程),至少包含一个线程,这个线程叫主线程.
     主线程:主线程在程序启东时被创建,用于执行main函数.
     只有一个主线程的程序,称作单线程程序
     在单线程程序中,主线程负责执行程序的所有代码(UI展现以及刷新,网络请求 ,本地存储等等).这些代码只能顺序执行,无法并发执行.
     */

    /*
     拥有多个线程的程序,称作多线程程序
     iOS允许用户开辟新的线程,相对于主线程来讲,这些线程,称作子线程.
     可以根据需要开辟若干个子线程.
     子线程和主线程都是独立的运行单元,各自的执行互不影响,因此能够并发执行.
     */

    /*
     单线程,多线程的区别
     单线程程序:只有一个线程,即主线程,代码顺序执行,容易出现代码阻塞(页面假死).
     多线程程序:有多个线程,线程间独立运行,能有效的避免代码阻塞,并且提高程序的运行性能.

     注意:iOS中关于UI的添加和刷新必须在主线程中操作
     */
    /*
     iOS多线程实现种类:
       1.NSThread;(轻量级的多线程)
       2.NSOperationQueue
       3.NSObject
       4.GCD
     */


    //NSThread有两种多线程的写法,一种手动取开辟,一种自动去开辟
    //自动开辟子线程
//    [NSThread detachNewThreadSelector:@selector(downloadmp3) toTarget:self withObject:nil];
    //本方法实现是手动的
//    NSThread *thread = [[NSThread alloc] initWithTarget:self selector:@selector(downloadmp3) object:nil];
    //手动取执行线程
//    [thread start];

    //结束线程有两种方式
    //第一种:给线程发送结束消息
//    [thread cancel];
//    //第二种:立即结束进程
//    [NSThread exit];

    //判断一个线程是否正在执行
//   BOOL bb = [thread isExecuting];
//    if (bb) {
//        NSLog(@"线程有执行");
//    }
//    //判断一个线程是否完成了任务(是否执行完毕)
//    BOOL aa = [thread isFinished];
//    if (aa) {
//        NSLog(@"任务完成");
//    }

    //NSObject实现异步后台执行
    //NSObject存在一个最简单的后台执行的方法(后台执行某个方法)
    //[thread performSelectorInBackground:@selector(<#selector#>) withObject:<#(nullable id)#>]






}
- (IBAction)StopMainThread:(id)sender {
    //怎么阻塞主线程,主线程中做耗时操作
    NSLog(@"%@--->",[NSThread currentThread]);
    long number = 0;
    for (long i = 0; i<=1000000000; i++) {
        number = number+i;
    }
    NSLog(@"%ld",number);

}

//用NSThread实现 用NSData下载一首MP3不允许卡住屏幕
- (IBAction)downLoadMP3:(id)sender {

    //点击button的时候开辟子线程
    //需要联网
    [NSThread detachNewThreadSelector:@selector(downloadMp3) toTarget:self withObject:nil];

}
-(void)downloadMp3
{
      NSString *str = @"http://60.190.216.110:8880/accompany_onlinePlay_130115exut/memberaccompany/songfolder/2009/11/13/608c3024c9f941ce8bf64f6ed4051c34.mp3";
    NSURL *url = [NSURL URLWithString:str];
    NSData *data = [NSData dataWithContentsOfURL:url];
    NSString *docpath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject];
    NSString *mp3path = [docpath stringByAppendingPathComponent:@"说谎.MP3"];
    NSLog(@"%@",mp3path);
    NSFileManager *manager = [NSFileManager defaultManager];
    [manager createFileAtPath:mp3path contents:data attributes:nil];

}

//锁(线程不重复访问)
- (IBAction)Touchlock:(id)sender {
    //开3个线程
    NSLock *lock = [[NSLock alloc] init];
    NSThread *t1 = [[NSThread alloc] initWithTarget:self selector:@selector(buyticket:) object:lock];
    NSThread *t2 = [[NSThread alloc] initWithTarget:self selector:@selector(buyticket:) object:lock];
    NSThread *t3 = [[NSThread alloc] initWithTarget:self selector:@selector(buyticket:) object:lock];
    [t1 start];
    [t2 start];
    [t3 start];

}
-(void)buyticket:(id)object
{
    NSLock *lock = (NSLock *)object;
    static NSInteger ticket= 10;
    while (YES) {
        [lock lock];
        sleep(1);
        ticket--;
        NSLog(@"%ld",ticket);
        if (ticket == 0) {
            break;
        }
        [lock unlock];
    }
}
//NSOperation(有两种开辟子线程的方式)
- (IBAction)NSOperation:(id)sender {
   /* //1.用子类创建
    NSInvocationOperation *op1 = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(StopMainThread2) object:nil];
        NSInvocationOperation *op2 = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(StopMainThread2) object:nil];
        NSInvocationOperation *op3 = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(StopMainThread2) object:nil];
    //创建线程池
    NSOperationQueue *queue = [[NSOperationQueue alloc] init];
    //设置最大并行个数
    //一个个执行
    [queue setMaxConcurrentOperationCount:1];
    //将三个线程放入池中
    [queue addOperation:op1];
    [queue addOperation:op2];
    [queue addOperation:op3];*/

    //第二种方式 需要自己创建一个类 继承自NSOperation
    //然后将耗时操作写到main函数
    MyNSOperation *myop1 = [[MyNSOperation alloc] init];
    MyNSOperation *myop2 = [[MyNSOperation alloc] init];
    MyNSOperation *myop3 = [[MyNSOperation alloc] init];
    //创建池
    NSOperationQueue *queue1 = [[NSOperationQueue alloc] init];
    [queue1 addOperation:myop1];
    [queue1 addOperation:myop2];
    [queue1 addOperation:myop3];






}
-(void)StopMainThread2
{
    //1+2+3+....+1000000000
    long number = 0 ;
    for (long i = 0 ; i<= 1000000000; i++) {
        number = number +i;
    }

    NSLog(@"%ld",number);
}

#pragma mark 主要开辟子线程的方式:GCD
- (IBAction)TouchGCD:(id)sender {
    //主要的(需要记住的)保留了一些c的东西
    //最常用的一种 一个子线程然后回到主线程
    //开子线程 子线程里可以直接回到主线程
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        long number = 0 ;
        for (long i = 0 ; i<= 100000000; i++) {
            number = number +i;
        }

        NSLog(@"%ld",number);
        //可以直接回到主线程
        dispatch_async(dispatch_get_main_queue(), ^{
            NSLog(@"计算结束了,回到主线程");
        });

    });

    //分组管理 所有线程执行结束汇总
    //创建queue
    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    //创建分组
    dispatch_group_t group = dispatch_group_create();
    //子线程1
    dispatch_group_async(group, queue, ^{
        sleep(1);
        NSLog(@"111");
    });
    //子线程2
    dispatch_group_async(group, queue, ^{
        sleep(2);
        NSLog(@"222");
    });
    //子线程3
    dispatch_group_async(group, queue, ^{
        sleep(3);
        NSLog(@"333");
    });
    //1,2,3走完了才能走的
    dispatch_group_notify(group, queue, ^{
        NSLog(@"1,2,3已经结束");
    });
    //"路障"(障碍)roadblock
    dispatch_queue_t queue1 = dispatch_queue_create(nil, DISPATCH_QUEUE_CONCURRENT);
    //线程1
    dispatch_async(queue1, ^{
        NSLog(@"1");
    });
    //线程2
    dispatch_async(queue1, ^{
        NSLog(@"2");
    });
    //"路障"(障碍物)
    dispatch_barrier_async(queue1, ^{
        NSLog(@"3障碍物走");
    });
    //线程3
    dispatch_async(queue1, ^{
        NSLog(@"4最后走");
    });

}


- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

@end


//自己写了一个继承自NSOperation的类
//.h没有东西
#import "MyNSOperation.h"

@implementation MyNSOperation

-(void)main
{
    long number = 0 ;
    for (long i = 0 ; i<= 1000000000; i++) {
        number = number +i;
    }

    NSLog(@"%ld",number);

}
@end
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值