Swift3 之函数参数的新变化

今天,在看 Then 源码时,发现了一处比较值得研究的地方

public func with(_ block: (inout Self) -> Void) -> Self {
    var copy = self
    block(©)
    return copy
}

这部分代码是在针对 Any 类型的协议扩展里实现的。这里 with 的语义是拷贝值类型并修改(代码中针对的是 Any,这里用值类型来说明问题)。可以看看官方的示例:

let newFrame = oldFrame.with { 
    $0.size.width = 200 
    $0.size.height = 100
}
newFrame.width // 200
newFrame.height // 100

注意,这里使用的是 inout 关键字,而且已经把它的位置放在了类型之前,这是 Swift3 的新变化 Adjusting inout Declarations for Type Decoration。

在函数调用时,如果传递的参数是引用类型,那么我们在函数中对参数的修改会直接影响到传进来的变量,这就是函数的副作用。

然而,如果传递的参数是值类型的话,我们在函数中对参数是不可以进行修改的,因为传参时函数会创建一个不变量来存储值,我们不可以对这个不变量进行修改。在 Swift2 中有个关键字 var 可以让函数创建一个变量来存储值,这样我们就可以在函数中对这个变量进行修改了。不过在 Swift3 中已经去掉了这个关键字 Removing var from Function Parameters。

如果想让值类型具备引用类型的语义,这时 inout 关键字就出场了。这个有点类似 C 语言中传递指针,我们在调用时需要加上 & 标识。这样,我们就可以愉快的对值类型进行修改了。不过,为了避免函数副作用,我们最后不要这样做。

你可能感兴趣的:(Swift3 之函数参数的新变化)