gpt4 book ai didi

swift - 闭包在定义或首次调用时是否分配内存?

转载 作者:行者123 更新时间:2023-11-28 15:06:16 24 4
gpt4 key购买 nike

闭包在定义或首次调用时是否分配内存?例如,当实例化名为 headerTitleHTMLElement 时,名称 asHTML 的闭包是否分配了内存,或者当 时在下一行asHTML() 被调用。此外,通过类提供了 deinit 实现。闭包有类似的功能吗?

class HTMLElement {
let name: String
let text: String?
lazy var asHTML: () -> String = {
return "<\(self.name)>\(self.text ?? "")</\(self.name)>"
}

init(name: String, text: String? = nil) {
self.name = name
self.text = text
}
deinit {print("\(name) is being deinitialized")}
}

var headerTitle: HTMLElement? = HTMLElement(name: "h1", text: "Welcome")
print(headerTitle!.asHTML())
headerTitle = nil

最佳答案

通常,闭包需要在其定义位置分配,以便捕获闭包内使用的闭包外部变量。但是,lazy 关键字使得闭包在第一次使用之前不会被声明。来自 Apple 的 documentation

A lazy stored property is a property whose initial value is not calculated until the first time it is used. You indicate a lazy stored property by writing the lazy modifier before its declaration.

我假设你所说的 deinit 是什么意思,因为闭包意味着释放对闭包中引用语义变量的任何强引用。您的示例来自 Apple 自己的 The Swift Programming Guide (Swift 4)。他们解释说这个例子有一个强引用循环,这意味着类实例持有对闭包的强引用,而闭包对实例有强引用。而且也不愿意彼此释放,导致实例永远不会被取消初始化。这是苹果的视觉效果: enter image description here

如果您进一步阅读本章的内容,他们谈到定义捕获列表以打破强引用循环。

lazy var asHTML: () -> String = {
[unowned self] in /*<-- Add self in the capture list, so the closure does not have a strong reference to the instance. */
if let text = self.text {
return "<\(self.name)>\(text)</\(self.name)>"
} else {
return "<\(self.name) />"
}
}

enter image description here

现在,当 headerTitle 设置为 nil 时,将显示 deinit 打印消息。

关于swift - 闭包在定义或首次调用时是否分配内存?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48434521/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com