• Semaphore回顾


    用途

    在多线程访问可变变量时,是非线程安全的。可能导致程序崩溃。此时,可以通过使用信号量(semaphore)技术,保证多线程处理某段代码时,后面线程等待前面线程执行,保证了多线程的安全性。使用方法记两个就行了,一个是wait(dispatch_semaphore_wait),一个是signal(dispatch_semaphore_signal)。根据dispatch_semaphore_wait的参数类型提示去创建信号量(dispatch_semaphore_t)即可。
    感觉原理跟PV操作如出一辙。

    不用semaphore时code:

    #import <Foundation/Foundation.h>
    
    int main(int argc, const char * argv[]) {
        @autoreleasepool {
            // insert code here...
            NSLog(@"Hello, World!");
            
            NSMutableArray *lArrM = [NSMutableArray array];
            for (int i = 0; i < 100; ++i) {
                dispatch_async(dispatch_get_global_queue(0, 0), ^{
                    [lArrM addObject:@(i)];
                });
            }
        }
        return 0;
    }
    

    运行结果

     SemephoreTest[3665:130800] Hello, World!
    SemephoreTest(3665,0x700001daa000) malloc: *** error for object 0x10077b2e0: pointer being freed was not allocated
    SemephoreTest(3665,0x700001daa000) malloc: *** set a breakpoint in malloc_error_break to debug
    SemephoreTest(3665,0x700001e2d000) malloc: *** error for object 0x102b00340: pointer being freed was not allocated
    SemephoreTest(3665,0x700001e2d000) malloc: *** set a breakpoint in malloc_error_break to debug
    SemephoreTest[3665:130800] lArrM.count:0
    (lldb) 
    

    用semaphore时code:

    //
    //  ViewController.m
    //  SemophoreTest
    //
    //  Created by LongMa on 2019/8/22.
    //  Copyright © 2019 . All rights reserved.
    //
    
    #import "ViewController.h"
    
    @interface ViewController ()
    
    @end
    
    @implementation ViewController
    
    - (void)viewDidLoad {
        [super viewDidLoad];
        
        NSMutableArray *lArrM = [NSMutableArray array];
        dispatch_semaphore_t lSema = dispatch_semaphore_create(1);//参数1,代表只能有1个线程同时访问被限制的代码。
        for (int i = 0; i < 1000; ++i) {
            dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
                dispatch_semaphore_wait(lSema, DISPATCH_TIME_FOREVER);//wait使信号量的值-1,如果结果为0,其他线程来访问时,需要等待。直到信号量的值大于0
                [lArrM addObject:@(i)];
                NSLog(@"lArrM.count:%zd",lArrM.count);
                dispatch_semaphore_signal(lSema);///wait使信号量的值+1,必须和dispatch_semaphore_wait配对使用。
            });
        }
        
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            NSLog(@"final  delayed lArrM.count:%zd",lArrM.count);
        });
    }
    
    
    @end
    
    
    

    运行结果(用commandlineTool运行代码时,log存在不完整问题):

    ...
     SemophoreTest[9092:877715] lArrM.count:999
     SemophoreTest[9092:877730] lArrM.count:1000
     SemophoreTest[9092:877696] final  delayed lArrM.count:1000
    
    学无止境,快乐编码。 没有一种不经过蔑视、忍受和奋斗就可以征服的命运。
  • 相关阅读:
    android 源码下载(Windows+Linux)
    Android Studio依赖包冲突 Execution failed for task ':app:transformResourcesWithMergeJavaResForDebug'.
    深入了解Java--1 绪论
    Android Studio 找不到R文件解决方法汇总
    Git学习历程
    word自动生成目录左对齐(缩进)问题
    Android Studio simpleUML(UML工具)使用详解
    android studio 常用快捷键
    当我们提起“女性权益”的时候,我们到底指的是什么?
    weakref模块和弱引用
  • 原文地址:https://www.cnblogs.com/Dast1/p/11392835.html
Copyright © 2020-2023  润新知