简体   繁体   English

在逻辑上无主,相当于弱! 在斯威夫特

[英]Is unowned logically equivalent to weak! in Swift

Will these blocks always fail under the same circumstances (when the closure is being executed but self was deallocated)? 这些块总是会在相同的情况下失败(当关闭被执行但是自我被解除分配时)?

{ [unowned self] in
    //use self
    self.number = self.number + 1
}

{ [weak self] in
    //use self!
    self!.number = self!.number + 1
}

Unowned reference does not keep strong reference to the self, but it makes an assumption that the object always has some value (is not nil) and if, some how self deallocates while executing the block, the above code crashes. 无主引用并不保留对self的强引用,但是它假设对象总是有一些值(不是nil),并且如果某些对象在执行块时自行解除分配,则上面的代码崩溃。

For the case of weak, as in your example, weak is an optional type inside the block, so there could also be a value or it could be nil. 对于弱的情况,如在您的示例中,weak是块内的可选类型,因此也可能有值或者它可能是nil。 It is your responsibility to check if the value exists and call methods on it. 您有责任检查值是否存在并在其上调用方法。 As above if you use unwrapping operator (!), when self has been deallocated, then it surely crashes. 如上所述,如果使用展开运算符(!),当self被释放时,它肯定会崩溃。 So, both the version of the code crashes, if it happens such that the block is still executing and self is deallocated in the mean time. 因此,代码的版本都会崩溃,如果它发生了,那么块仍在执行,并且self同时被释放。

So, I suggest to use weak to safeguard such crashes using the optional checks, 因此,我建议使用weak来使用可选的检查来保护此类崩溃,

{ [weak self] in
    if let me = self {
       me.number = me.number + 1
    }
}

Yes, those are equivalent. 是的,那些是等价的。 That is the point of unowned -- it's just like weak , except that you don't have to deal with an optional and unwrap it, because its type is the unwrapped non-optional type; 这是unowned的点 - 它就像weak一样,除了你不需要处理一个可选的并解开它,因为它的类型是unwrapped非可选类型; it is weak that is always forcibly unwrapped at every appearance. 它很weak ,总是在每次出现时被强行打开。

Should use it like this 应该像这样使用它

{ [weak self] in

    guard let weakSelf = self else {
       return 
    }

    weakSelf.number = weakSelf.number + 1
}

Thanks to @José 's comment, be aware that even though the following code works at the moment, but it is considered a compiler bug and should be avoided https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160118/007425.html . 感谢@José的评论,请注意,即使以下代码目前有效,但它被认为是编译器错误,应该避免使用https://lists.swift.org/pipermail/swift-evolution/Week- -Mon-20160118 / 007425.html

You can also unwrap self like this: 你也可以这样打开self

{ [weak self] in

    guard let `self` = self else {
       return 
    }

    // Now you can use `self` safely
    self.number = self.number + 1
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM