当我用 Google 搜索“State vs ObservedObject”时,第一个结果来自 Hacking with Swift,它说@ObservedObject
:
这与@State 非常相似,只是现在我们使用的是外部引用类型,而不是像字符串或整数这样的简单本地属性。
我可以@ObservedObject
用来创建持久状态吗?它是否像@State
简单属性和@ObservedObject
复杂对象一样简单,还是有更多细微差别?
当我用 Google 搜索“State vs ObservedObject”时,第一个结果来自 Hacking with Swift,它说@ObservedObject
:
这与@State 非常相似,只是现在我们使用的是外部引用类型,而不是像字符串或整数这样的简单本地属性。
我可以@ObservedObject
用来创建持久状态吗?它是否像@State
简单属性和@ObservedObject
复杂对象一样简单,还是有更多细微差别?
@ObservedObject
不持久状态我可以
@ObservedObject
用来创建持久状态吗?
就其本身而言,你不能。Apple文档有这样的说法@State
:
给定类型的持久值,视图通过它读取和监视该值。
但我发现没有提到持久性,@ObservedObject
所以我构建了这个小演示,确认@ObservedObject
不持久状态:
class Bar: ObservableObject {
@Published var value: Int
init(bar: Int) {
self.value = bar
}
}
struct ChildView: View {
let value: Int
@ObservedObject var bar: Bar = Bar(bar: 0)
var body: some View {
VStack(alignment: .trailing) {
Text("param value: \(value)")
Text("@ObservedObject bar: \(bar.value)")
Button("(child) bar.value++") {
self.bar.value += 1
}
}
}
}
struct ContentView: View {
@State var value = 0
var body: some View {
VStack {
Spacer()
Button("(parent) value++") {
self.value += 1
}
ChildView(value: value)
Spacer()
}
}
}
每当您单击value++
按钮时,都会导致重新渲染,ChildView
因为value
属性已更改。当视图由于属性更改而重新渲染时,它的@ObservedObject
s 将被重置
相反,如果您向 中添加一个@State
变量,ChildView
您会注意到在重置时它的值不会@ObservedObject
重置。
@ObservedObject
要使用 保持状态,请在父视图中@ObservedObject
实例化混凝土。因此,要修复前面的示例,将如下所示:ObservableObject
@State
struct ChildView: View {
let value: Int
@ObservedObject var bar: Bar // <-- passed in by parent view
var body: some View {
VStack(alignment: .trailing) {
Text("param value: \(value)")
Text("@ObservedObject bar: \(bar.value)")
Button("(child) bar.value++") {
self.bar.value += 1
}
}
}
}
struct ContentView: View {
@State var value = 0
@State var bar = Bar(bar: 0) // <-- The ObservableObject
var body: some View {
VStack {
Spacer()
Button("(parent) value++") {
self.value += 1
}
ChildView(value: value, bar: bar).id(1)
Spacer()
}
}
}
类的定义与Bar
第一个代码示例相同。现在我们看到,即使value
属性发生变化,该值也不会重置: