てくてくテック

気ままに開発のメモを書いていこうと思います。主にSwiftかと。

Swift3でのclosure

はじめに

Swift3にした時にclousureの部分の書き方が変わっていたなーというメモです

変更点

非同期の時は@escapingをつける

Swift2まではデフォルトが@escapingの状態で@noescapeにする際に明示的に@noescapeにするという文法だったのに、Swift3から逆転しました。 @esapingにするとどうなのか?という話はSwift 3 の @escaping とは何かがわかりやすいので、こちらを参照していただけたら良いと思います。

第一引数の前に _をつける

どうもclosureの第一引数の前に_をつけないといけないみたいです。
これはメソッドの第一引数にラベルを書くという文法の変更に近いお話です。この文法では従来のように第一引数にラベルをつけない場合は_をつけることになってます。Establish consistent label behavior across all parameters including first labelsの話です。Swift2では***With???みたいに第一引数のラベルのようなものをWithの後ろにくっつけるような書き方になっていたのを***(???)という感じにすっきりと書けるようになりました。 例えばSwift2では

func fileWithName(name: String){

}

こうだったのに対しSwift3ではこうなります。

func file(name: Strint){

}

//Swift2式で書く場合
func fileWithName(_ name: String){

}

メソッドの文法で第一引数にラベルをつけない場合は_をつけるのはわかったのですが、ではなぜclosureの第一引数では_をつけなければならないのでしょうか?
How do you document the parameters of a function's closure parameter in Swift 3?のstack over flowの回答のなかに

As @Arnaud pointed out, you can use _ to prevent having to use the parameter label when calling the closure:

In fact, this is the only valid approach in Swift 3 because parameter labels are no longer part of the type system (see SE-0111).

とありどうもRemove type system significance of function argument labelsが原因のようです。ここはまだちゃんと解読できていないのでそのうち読んだら追記します。