Sur*_*gch 11 weak-references automatic-ref-counting swift
我今天再次尝试尝试理解Swift中的保留周期和弱引用.通过阅读文档,我看到了以下代码示例,其中一个引用变量被标记为weak
阻止保留周期:
class Person {
let name: String
init(name: String) { self.name = name }
var apartment: Apartment?
deinit { print("\(name) is being deinitialized") }
}
class Apartment {
let unit: String
init(unit: String) { self.unit = unit }
weak var tenant: Person? // <---- This var is marked as 'weak'
deinit { print("Apartment \(unit) is being deinitialized") }
}
var john: Person?
var unit4A: Apartment?
john = Person(name: "John Appleseed")
unit4A = Apartment(unit: "4A")
john!.apartment = unit4A
unit4A!.tenant = john
john = nil // prints "John Appleseed is being deinitialized"
unit4A = nil // prints "Apartment 4A is being deinitialized"
Run Code Online (Sandbox Code Playgroud)
让变量变弱都有问题吗?也就是说,在Person
课堂上,我可以将apartment
变量变弱,以便我拥有
class Person {
// ...
weak var apartment: Apartment? // added 'weak'
// ...
}
class Apartment {
// ...
weak var tenant: Person?
// ...
}
Run Code Online (Sandbox Code Playgroud)
其中有两个相互引用的弱变量.
我在游乐场测试了它似乎工作正常,但有没有强烈的理由不这样做?在这种情况下似乎没有自然的亲子关系.
Wai*_*ain 14
你可以做到这一点.唯一的副作用是你需要确保其他东西保留了人和公寓.在原始代码中,您只需要保留人员,公寓(与人相关)将保留给您.
严格来说,当公寓被拆除时人们没有被杀死,当人们死亡时公寓没有被拆除,因此这种情况下的弱参考是有道理的.通常最好考虑您想要的关系和所有权模型,然后决定如何实现这一目标.
为了增加接受的答案,这里是一个演示行为的具体例子.
试试这是一个游乐场:
class Person {
let name: String
init(name: String) { self.name = name }
weak var apartment: Apartment?
deinit { print("\(name) is being deinitialized") }
}
class Apartment {
let unit: String
init(unit: String) { self.unit = unit }
weak var tenant: Person? // <---- This var is marked as 'weak'
deinit { print("Apartment \(unit) is being deinitialized") }
}
class Test {
var person: Person
init() {
person = Person(name: "Fred")
let unit2B = Apartment(unit: "2B")
person.apartment = unit2B
unit2B.tenant = person
print(person.apartment!.unit)
}
func test() {
print(person.apartment!.unit)
}
}
func go() {
let t = Test()
t.test() // crashes here!
}
go()
Run Code Online (Sandbox Code Playgroud)
在init
课堂上Test
,已创建的公寓由本地变量保留unit2B
.当init
完成后,公寓将被释放,因为不再有任何的强引用抱着它,所以当程序崩溃test
,是因为所谓的person.apartment
现在nil
.
如果删除weak
from weak var apartment
in class Person
,则此示例不会崩溃,因为创建的公寓由class属性init
保留的person
who保留person
.
修复示例的另一种方法是使其unit2B
成为属性class Test
.然后公寓将有一个强大的参考持有它所以unit2B
不会被取消分配后init
.
如果weak
从weak var apartment
in class Person
和from weak var tenant
中删除class Apartment
,那么示例不会崩溃,但是由于两个对象彼此保持强引用而创建的保留周期Person
,Apartment
因此不会释放也不会释放.
归档时间: |
|
查看次数: |
1160 次 |
最近记录: |