Swift 值类型在多线程中真的安全吗?
苹果说,“如果你使用Value-type,你可以安全地在线程间传递值的副本,而无需同步。”。但我最近看到并发崩溃,与苹果指南不符 我看到和苹果的指南说“值类型在多线程中是安全的”,所以我认为“值类型是原子的!”但最近我看到下面代码中并发崩溃Swift 值类型在多线程中真的安全吗?,swift,concurrency,Swift,Concurrency,苹果说,“如果你使用Value-type,你可以安全地在线程间传递值的副本,而无需同步。”。但我最近看到并发崩溃,与苹果指南不符 我看到和苹果的指南说“值类型在多线程中是安全的”,所以我认为“值类型是原子的!”但最近我看到下面代码中并发崩溃 class ClassB: NSObject { func readSomeValue() { print(classA.someValue) } let classA = ClassA() } class ClassA
class ClassB: NSObject {
func readSomeValue() {
print(classA.someValue)
}
let classA = ClassA()
}
class ClassA: NSObject {
private(set) var someValue: StructA? {
didSet{
if oldValue != self.someValue { self.someFunction(self.someValue) }
}
}
private func modifySomeValue(_ newValue: StructA) {
self.someValue = newValue
}
}
struct StructA {
var a: Double
var b: String?
}
在thread1中执行readSomeValue()并在thread2中执行modifySomeValue()时发生并发崩溃。
为什么并发崩溃会发生?值类型在多线程中不安全吗?有几个观察结果:
类。当然,您的引用类型有一个value-type属性,但这不会改变您正在跨线程共享引用类型对象实例的单个实例的事实。为了享受线程安全,您必须手动同步与该对象及其属性的交互
var object = StructA(a: 42, b: "foo")
DispatchQueue.global().async {
print(object)
}
object.b = "bar"
但通过添加捕获列表,全局队列将拥有自己的对象副本,从而恢复线程间的线程安全交互,因为每个线程都有自己的对象副本:
var object = StructA(a: 42, b: "foo")
DispatchQueue.global().async { [object] in
print(object)
}
object.b = "bar"