Swift 为什么设计 inout 关键字?

2021-05-08 17:19:18 +08:00
 fffang

从语言设计的角度上看,有什么必要性么?如果像 OC 那样会发生什么情况?

4132 次点击
所在节点    iDev
8 条回复
Elethom
2021-05-08 17:31:17 +08:00
OC 也可以丢个 & 进去啊,你这是两个语言都没入门吗,先学会一个再学另一个吧。
zjw7sky
2021-05-08 17:36:43 +08:00
传值、传址
fffang
2021-05-08 17:37:43 +08:00
@Elethom OC 是可以的。
可是 OC 中参数 Array 是可以 append 元素的,而 Swift 好像不可以?
MrKrabs
2021-05-08 17:46:46 +08:00
value 和 reference 不一样
superpeaser
2021-05-08 17:51:23 +08:00
@fffang OC 的参数 array 传的可变数组的地址
YYYeung
2021-05-09 00:16:05 +08:00
Swift 的 inout 表示操作的是指针

而有一些数据结构,如数组,在 Swift 中是值传递,在 OC 中是引用传递,这会发生什么事?

在 OC 中,当将一个数组作为一个参数传到另一个函数或方法中,并在该函数体或方法体中,对这个数组 append 一个元素,是没有什么反“直觉”的事发生,一切都很自然

而在 Swift 中,实际上是 append 到了一个新数组,原来的数组是没有改变的,此时,要实现 OC 的“直觉”效果,就需要用到 inout 了
0x00ZhouJialei
2021-05-09 03:33:06 +08:00
先说动机 , 引用自 https://docs.swift.org/swift-book/LanguageGuide/Functions.html In-Out Parameters 章节:
Function parameters are constants by default. Trying to change the value of a function parameter from within the body of that function results in a compile-time error. This means that you can’t change the value of a parameter by mistake. If you want a function to modify a parameter’s value, and you want those changes to persist after the function call has ended, define that parameter as an in-out parameter instead.

再说行为, 引用自 https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID545:
In-out parameters are passed as follows:
1. When the function is called, the value of the argument is copied.
2. In the body of the function, the copy is modified.
3.When the function returns, the copy’s value is assigned to the original argument.
This behavior is known as copy-in copy-out or call by value result. For example, when a computed property or a property with observers is passed as an in-out parameter, its getter is called as part of the function call and its setter is called as part of the function return.

多说几句,编译器有可能会把 inout 优化为所谓的传址(call-by-reference),但是官方特意指出开发者们不能依赖这个行为:
As an optimization, when the argument is a value stored at a physical address in memory, the same memory location is used both inside and outside the function body. The optimized behavior is known as call by reference;
Write your code using the model given by copy-in copy-out, without depending on the call-by-reference optimization, so that it behaves correctly with or without the optimization

不严谨的验证方式是,传一个带有 willSet 或者 didSet 的变量到一个 function 的 inout 参数内,就算在 function 内不改变值,willSet 或者 didSet 也会触发
iOCZ
2021-05-09 12:32:16 +08:00
不是必须,但是便利吧。常见的是要返回操作成功与否,还要返回处理结果,返回元组当然可以,但是不那么方便。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/775701

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX