iOS讀寫安全方案


本人已遷移博客至掘進,以后會在掘進平台更新最新的文章也會有更多的干貨,歡迎大家關注!!!https://juejin.im/user/588993965333309

 

思考如下實現以下場景?

  • 同一時間,只能有1個線程進行寫的操作
  • 同一時間,允許多個線程進行讀的操作
  • 同一時間,不允許既有寫的操作,又有讀的操作

上面的場景就是典型的“多讀單寫”,經常用於文件等數據的讀寫操作,iOS的實現方案有

  1. pthread_rwlock:讀寫鎖
  2. dispatch_barrier_async:異步柵欄調用

 

1.  pthread_rwlock 互斥鎖(會休眠)

1.1  知識講解

 

1.2  demo實例講解

#import "ViewController.h"
#import <pthread.h>

@interface ViewController ()
@property (assign, nonatomic) pthread_rwlock_t lock;
@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    
    // 初始化鎖
    pthread_rwlock_init(&_lock, NULL);
    
    dispatch_queue_t queue = dispatch_get_global_queue(0, 0);
    
    for (int i = 0; i < 10; i++) {
        dispatch_async(queue, ^{
            [self read];
        });
        dispatch_async(queue, ^{
            [self write];
        });
    }
}


- (void)read {
    //讀鎖
    pthread_rwlock_rdlock(&_lock);
    
    sleep(1);
    NSLog(@"%s", __func__);
    
    pthread_rwlock_unlock(&_lock);
}

- (void)write
{
    //寫鎖
    pthread_rwlock_wrlock(&_lock);
    
    sleep(1);
    NSLog(@"%s", __func__);
    
    pthread_rwlock_unlock(&_lock);
}

// pthread_rwlock_destroy 是pthread鎖,要銷毀
- (void)dealloc
{
    pthread_rwlock_destroy(&_lock);
}

 

1.3  執行結果

  

2.  dispatch_barrier_async 柵欄

2.1  知識講解

這個函數傳入的並發隊列 必須是自己通過dispatch_queue_create創建的

如果傳入的是一個串行隊列或者是全局的並發隊列,那這個函數便等同於dispatch_async 函數的效果,起不到柵欄的作用

 

2.2  demo實例講解

#import "ViewController.h"
#import <pthread.h>

@interface ViewController ()
@property (strong, nonatomic) dispatch_queue_t queue;
@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    
    self.queue = dispatch_queue_create("rw_queue", DISPATCH_QUEUE_CONCURRENT);
    
    for (int i = 0; i < 10; i++) {
        dispatch_async(self.queue, ^{
            [self read];
        });
        
        dispatch_async(self.queue, ^{
            [self read];
        });
        
        dispatch_async(self.queue, ^{
            [self read];
        });
        
        dispatch_barrier_async(self.queue, ^{
            [self write];
        });
    }
}


- (void)read {
    sleep(1);
    NSLog(@"read");
}

- (void)write
{
    sleep(1);
    NSLog(@"write");
}

@end

 

2.3  執行結果

 

上面就是兩種常用的iOS 讀寫安全操作,歡迎指正!!!


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM