知道Swift中弱变量何时变为零? [英] Know when a weak var becomes nil in Swift?

查看:88
本文介绍了知道Swift中弱变量何时变为零?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我的弱var视图:UIView?在我的类Button {} 中。有没有办法知道什么时候查看失去了它的引用并变成 nil

Let's say I have a weak var view: UIView? in my class Button {}. Is there any way to know when view loses its reference and becomes nil?

我尝试使用弱变量视图:UIView? {} (又名计算属性),以覆盖 set {} ,但这不起作用,因为现在它是一个计算属性,可以不存储弱引用(多么烦人!)。

I tried using weak var view: UIView? {} (aka a computed property) in order to override set {}, but that didn't work because now it's a computed property and can't store a weak reference (how annoying!).

编辑:

@fqdn 的答案无法使用此代码...在Xcode Playground中试用

@fqdn's answer didn't work with this code... Try it in an Xcode Playground

import UIKit

class Test {
  weak var target: UIView? {
    willSet {
      if !newValue { println("target set to nil") }
      else { println("target set to view") }
    }
  }
}

class Button {
  var view: UIView? = UIView()
}

var t = Test()
var b = Button()
t.target = b.view
b.view = nil // t.target's willSet should be fired here

你的输出控制台应显示:

Your output console should display:

target set to view
target set to nil

我的控制台显示

target set to view

b.view 是UIView实例的强引用。 t.target 是弱引用。因此,如果 b.view 设置为 nil ,则取消分配UIView实例并 t .target 将等于nil。

b.view is the strong reference for the UIView instance. t.target is the weak reference. Therefore, if b.view is set to nil, the UIView instance is deallocated and t.target will be equal to nil.

推荐答案

如果你的按钮持有对另一个视图的引用,它应该是该视图的所有者(即,它应该持有一个强引用),或者当该视图消失时它不应该关心(即,它的弱引用变为零)。当弱引用变为无效时,没有通知nil,这是设计的。

If your button is holding a reference to another view, it should either be an owner of that view (i.e., it should hold a strong reference) or it should not care when that view goes away (i.e., its weak reference to it becomes nil.) There is no notification when weak references become nil, and that is by design.

特别是,当弱引用变为nil时,不会调用Swift属性观察器,如下面的代码所示:

In particular, Swift property observers are not called when weak references become nil, as the following code demonstrates:

class A : CustomStringConvertible {
    var s: String?

    init(s: String) {
        self.s = s;
        print("\(self) init")
    }

    deinit {
        print("\(self) deinit")
    }

    var description: String {
        get { return "[A s:\(s ?? "nil")]" }
    }
}

class B : CustomStringConvertible {
    weak var a:A? {
        willSet {
            print("\(self) willSet a")
        }
        didSet {
            print("\(self) didSet a")
        }
    }

    init(a: A?) {
        self.a = a
        print("\(self) init")
    }

    deinit {
        print("\(self) deinit")
    }

    var description: String {
        get { return "[B a:\(a == nil ? "nil" : String(describing: a!))]" }
    }
}

func work() {
    var a: A? = A(s: "Hello")
    var b = B(a: a)
    print("\(b)")
    a = nil
    print("\(b)")
    b.a = A(s: "Goodbye")
}

work()

当调用 work()时,控制台会给出以下输出:

When work() is called, the console gives the following output:

[A s:Hello] init
[B a:[A s:Hello]] init
[B a:[A s:Hello]]
[A s:Hello] deinit
[B a:nil]
[A s:Goodbye] init
[B a:nil] willSet a
[B a:[A s:Goodbye]] didSet a
[A s:Goodbye] deinit
[B a:nil] deinit

请注意,在A取消分配的实例和在B变为nil的实例中的弱引用都不是属性观察者调用的。只有在分配给B.a的直接情况下才会调用它们。

Notice that in neither case of the instance of A deallocating and its weak reference in the instance of B becoming nil are the property observers called. Only in the direct case of assignment to B.a are they called.

这篇关于知道Swift中弱变量何时变为零?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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