结构是不可变的,这意味着它们不能改变。我必须清楚地误解了整个概念,因为似乎有时我确实可以更改结构,而有时则不能。
考虑这段代码:
struct SomeStruct: View {
var someProperty = ""
var someComputedProperty: String {
get { someProperty }
set { someProperty = "a" } // WORKD
}
func someFunc() {
someProperty = "b" // ERROR; BUT WORKS WITH mutating func
}
var body: some View {
Button("SomeButton", action: {
someProperty = "c" // ERROR
})
}
}
struct SomeOtherStruct {
func someOtherFunct() {
var someStruct = SomeStruct()
someStruct.someProperty = "THIS WORKS"
}
}
唯一实际上不允许更改结构的地方是在
Button
closure
中。为什么有时允许,有时不允许?或者我只是误解了不变性实际上意味着什么?
结构不是一成不变的。然而,它们被称为“值类型”,这意味着它们在传递给函数时具有隐式复制。如果您将一个结构体传递给一个函数,并对函数内部的结构体执行一个操作来改变它,则该结构体的outer版本保持不变,因为传递给函数的实际上是一个副本。 考虑以下因素:
struct Foo {
var value: Int
}
func bar(_ f: Foo) {
f.value += 1
}
var f = Foo(value: 1)
bar(f)
// f.value is still 1
为了改变函数内的结构,您必须将其显式传递为
inout
:
func baz(_ f: inout Foo) {
f.value += 1
}
baz(&f)
// f.value is now 2
编辑:请注意,我没有使用过 Swift UI,而且我真的不知道结构的行为如何应用于该特定框架。这个答案是关于一般意义上的 Swift 中的结构。
var someStruct = SomeStruct()
someStruct.someProperty = "THIS WORKS"
用“let”定义的变量是不可变的:
let someStruct = SomeStruct()
someStruct.someProperty = "NOPE" //doesn't work
与结构体中的变量相同。除了 init 之外,即使结构变量是
var
,也不允许突变。
struct SomeStruct: View {
let someProperty!
}
var someStruct = SomeStruct()
someStruct.someProperty = "NOPE" //Can only set in init