如何同步对具有didSet的属性的访问? [英] How do I synchronize access to a property that has didSet?

查看:68
本文介绍了如何同步对具有didSet的属性的访问?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何同步访问使用didSet的属性(使用GCD或objc_sync_enter)?

How do I synchronize access of a property that uses didSet (using GCD or objc_sync_enter)?

我有一个带有属性观察器的属性.如何使用私有队列同步属性的获取/设置

I have a property that has a property observer. How can I use a private queue to synchronize get/set of the property

var state: State = .disconnected {
  // Q: How to sync get/set access here?
  didSet {
    // do something
  }
}

推荐答案

最简单的方法是使用串行队列

simplest way is using a serial queue

import Dispatch

struct S {
    private var i: Int = 0 {
        didSet {
            print("someone did set new value:", i)
        }
    }
    private let queue = DispatchQueue(label: "private", qos: .userInteractive) // high priority
    var value: Int {
        get {
            return queue.sync {
                return i
            }
        }
        set {
            if newValue == value {
                return
            }
            queue.sync {
                i = newValue
            }
        }
    }
}

更高级的示例使用并发读取和同步屏障进行写入

more advanced example use concurrent reading and sync barrier for writing

import Dispatch

struct S {
    private var i: Int = 0 {
        didSet {
            print("someone did set new value:", i)
        }
    }
    private let queue = DispatchQueue(label: "private", qos: .userInteractive, attributes: .concurrent) // high priority
    var value: Int {
        get {
            return queue.sync {
                return i
            }
        }
        set {
            if newValue == value {
                return
            }
            queue.sync(flags: .barrier) {
                i = newValue
            }
        }
    }
}

对于类属性,您可以使用并发专用队列,并发地从其他线程中读取,并使用屏障异步调度写操作

in the case of class property, you can use a concurrent private queue and read from different thread concurrently and dispatch write asynchronously with a barrier

import Dispatch

class S {
    private var i: Int = 0 {
        didSet {
            print("someone did set new value:", i)
        }
    }
    private let queue = DispatchQueue(label: "private", qos: .userInteractive, attributes: .concurrent) // high priority
    var value: Int {
        get {
            return queue.sync {
                return i
            }
        }
        set {
            if newValue == value {
                return
            }
            queue.async(flags: .barrier) { [unowned self] in
                self.i = newValue
            }
        }
    }
}

这篇关于如何同步对具有didSet的属性的访问?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆