嵌套嵌套Swift结构中的数组

时间:2020-10-30 03:50:51

标签: swift

我是Swift的新手,因此,感谢您对我的方法提出的任何反馈或建议。作为参考,我正在使用Xcode 12.1和Swift 5.3。本质上,我有一系列struct,其中一个具有字符串数组。我想做的是将一个字符串附加到该数组。考虑以下代码:

struct Collection {
    var things: [Thing] = []
    
    mutating func add(_ thing: Thing) {
        things.append(thing)
    }
}

struct Thing {
    var messages: [String] = []

    mutating func add(_ message: String) {
        messages.append(message)
    }
}

var collection = Collection()
collection.add(Thing())
var thing = collection.things.first
thing!.add("test")


print(collection.things.first!.messages.count)

我期望最后一行打印1,但是它却打印0!编译也不显示任何错误。如果我更改代码以使struct Thingclass Thing,并从其mutating方法中删除add关键字,则代码可以正常工作。

话虽如此,我不明白为什么我的原始代码无法按预期工作。我可以在Thing后面附加一个Collection实例,但是在事实之后不能在同一Thing实例上附加一个字符串。

我是否误解了mutating关键字的工作原理?

1 个答案:

答案 0 :(得分:2)

如果您这样做,将会得到预期的1

print(thing!.messages.count)

因为您已将"test"添加到thing.messages,而不是collection.things.first!.messages

“现在等一下!”我听到你说:“我在前一行刚刚说过var thing = collection.things.first!添加到thing.messages并不意味着添加到collection.things.first!.messages吗?”。

这是因为结构具有值语义。当您执行var thing = collection.things.first时,您是在说“将collection.things.first的值复制到名为thing的变量中”。您不是说“变量thing现在引用collection.things.first相同。”也就是说,Thing必须是引用类型(class)。

因此,现在您有两个具有相同值的副本,一个在thing中,一个在collection.things.first中。您更改了存储在thing中的副本。另一个副本不受影响。