Ios getter和setter自定义并发队列同步上的竞速条件
我有以下代码,据我所知,这些代码应该提供对Ios getter和setter自定义并发队列同步上的竞速条件,ios,swift,grand-central-dispatch,swift4,Ios,Swift,Grand Central Dispatch,Swift4,我有以下代码,据我所知,这些代码应该提供对\u的线程安全读写。我的isolationQueue是一个并发队列,因此需要保持不变。我在此队列上调用多个独立的异步操作来计算各种图像的预测。不同调用之间的唯一共享项是设置预测时的值 var isolationQueue = DispatchQueue.global(qos: .default) var _predictions: [Int:[Prediction]] = [:] var predictions:[Int: [Predict
\u
的线程安全读写。我的isolationQueue是一个并发队列,因此需要保持不变。我在此队列上调用多个独立的异步操作来计算各种图像的预测。不同调用之间的唯一共享项是设置预测时的值
var isolationQueue = DispatchQueue.global(qos: .default)
var _predictions: [Int:[Prediction]] = [:]
var predictions:[Int: [Prediction]] {
get {
var result: [Int: [Prediction]]!
isolationQueue.sync {
result = _predictions
}
return result
}
set(value) {
isolationQueue.sync {
self._predictions = value
}
}
}
然而,由于某些原因,线程消毒剂似乎检测到getter和setter之间的竞速情况
我遗漏了什么吗?全局调度队列是并发队列,因此它们不能是并发队列 用于防止并发访问资源 为此,您应该定义自己的串行调度队列:
var isolationQueue = DispatchQueue(label: "my.queue.identifier")
对于您的情况,使用DispatchSemaphore()更简单,开销更小。代码看起来像
var isolationSem = DispatchSemaphore(value: 1)
var _predictions: [Int:[Prediction]] = [:]
var predictions:[Int: [Prediction]] {
get {
var result: [Int: [Prediction]]!
isolationSem.wait()
result = _predictions
isolationSem.signal()
return result
}
set(value) {
isolationSem.wait()
self._predictions = value
isolationSem.signal()
}
}
有关DispatchSemaphore不适用的情况,请参阅。isolationQueue是如何定义的?是串行调度队列吗?更新了问题。它是全球性的,因此我相信它会同时发生
var isolationQueue=DispatchQueue.global(qos:.默认值)
在并发队列中执行时,使用sync
不会防止其他线程访问资源?在并发队列上是否还有确保串行访问的方法?@RezaShirazian:sync
意味着调用线程等待完成,但从不同线程调度的块可以同时执行。下面是对4种可能组合的一个很好的概述:。我该如何处理sync
呢?如果我的isolationQueue
是串行的sync
在这种情况下似乎没有多大意义。@RezaShirazian:isolationQueue.async{…}
将立即返回,而不等待执行该项。同步/异步和串行/并发是独立的参数。请看一看并尝试一下(您可以在setter上使用async
,但不能在getter方法上使用。)谢谢Martin。我想我明白了。首先,我的队列需要保持并发,因为我需要运行多个独立的异步操作来计算预测。将我的setter设置为async(标志:.barrier)
可确保在设置预测字典时,此队列上的其他操作不会修改它。