Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Swift 4 の変更点

Swift 4 の変更点

Yasuhiro Hatta

June 16, 2017
Tweet

Other Decks in Programming

Transcript

  1. ⽂字列が使いやすくなった ◦ Swift 3 では good.characters.count のように String.CharacterView を経由して⽂字列操作 をしていた

    ◦ Swift 4 では String が BidirectionalCollection と RangeReplaceableCollection を実装 ◦ String が Collection になった let good = "Good!!" _ = good.count // 7 SE-0163 String Revision: Collection Conformance, C Interop, Transcoding
  2. Key-Value ペアの Sequence から Dictionary を作れるようになった SE-0165 Dictionary & Set

    Enhancements let pairs: [(String, Int)] = [("a", 10), ("b", 20), ("c", 30)] let dict = Dictionary(uniqueKeysWithValues: pairs) dict["a"] // 10 dict["b"] // 20
  3. Dictionary のフィルタ結果が Dictionary で返ってくるようになった ◦ Swift 3 では Array<(K, V)>

    で返ってきていた let pairs: [(String, Int)] = [("a", 10), ("b", 20), ("c", 30)] let dict = Dictionary(uniqueKeysWithValues: pairs) let filtered = dict.filter { $0.value == 20 } filtered["a"] // nil filtered["b"] // 20
  4. Dictionary の mapValues() で Value を置換 let pairs: [(String, Int)]

    = [("a", 10), ("b", 20), ("c", 30)] let dict = Dictionary(uniqueKeysWithValues: pairs) let mapped = dict.mapValues { $0 * 10 } mapped["a"] // 100 mapped["b"] // 200
  5. Dictionary の Default Value を指定 let dict = ["a": 10]

    _ = dict["b"] ?? 0 _ = dict["b", default: 0] // New!!
  6. Sequence からグループを作る let array = ["a", "", "b", ""] let

    dict: Dictionary<Bool, [String]> = Dictionary(grouping: array, by: { $0.isEmpty }) dict[true] // ["", ""] dict[false] // ["a", "b"]
  7. オブジェクトのシリアライズ ◦ 標準ライブラリに Codable というプロトコルが追加された ◦ public typealias Codable =

    Decodable & Encodable ◦ JSON と Plist のシリアライザは標準で提供される SE-0166 Swift Archival & Serialization SE-0167 Swift Encoders
  8. struct User: Codable { let name: String let age: Int

    } let originalUser = User(name: "xx yy", age: 20) // オブジェクトから JSON データにエンコード let jsonData: Data = try! JSONEncoder().encode(originalUser) // => {"name":"xx yy","age":20} // JSON データをオブジェクトにデコード let decodedUser: User = try! JSONDecoder().decode(User.self, from: jsonData)
  9. One-sided Ranges SE-0172 One-sided Ranges let array = ["a", "b",

    "c", "d", "e"] let subArray1 = array[2...] // ["c", "d", "e"] let subArray2 = array[...2] // [“a”, “b”, "c"] for i in 0... { // 無限ループ。このコードを Playground 貼り付けないでください }
  10. extension から private な定義へア クセス可能 (同じファイル内のみ) SE-0169 Improve Interaction Between

    private Declarations and Extensions class C { private var value: Int = 0 } extension C { func add(_ v: Int) { // extension から private 変数にアクセス value += v // ok (Swift 4) } } class OtherClass { func f() { let c = C() // 同じファイル内でも、別のクラスからは private 変数にアクセスできない let v = c.value // error (従来通り) } }
  11. 変数宣⾔時に class と protocol を 同時に指定 ◦ Swift 3 ではプロトコルを

    & でつないで複数指定できたが、プロトコル以外と組み合わせるこ とができなかった ◦ Swift 4 ではプロトコル以外と組み合わせることができるようなった SE-0156 Class and Subtype existentials protocol P {} class C {} class D: C, P {} let d: C & P = D()
  12. ⧵ で KeyPath ◦ #keyPath() という書き⽅がある ◦ Darwin (iOS, macOS,

    …) でしか使えない ◦ NSObject を継承していないと使えない ◦ コンパイル後、⽂字列になる → 型情報がない、⽂字列をパースするので遅い ◦ などの問題 ◦ Swift 4 でこの問題を解決 ◦ 書き⽅ ◦ ⧵<Type>.<path> ◦ ⧵.<path> ◦ ⽂脈から型がわかる場合は <Type> を省略可能 ◦ Xcode 9 beta 1 ではまだ完全に実装されていませんでした・・・ SE-0161 Smart KeyPaths: Better Key-Value Coding for Swift
  13. @objc の⾃動判別に制限 ◦ @objc メソッドのオーバーライド、@objc プロトコルの実装、@IBAction、@IBOutlet、 @IBInspectable、@GKInspectable、@NSManaged、dynamic 変数は @objc が⾃動的に

    付与されていた ◦ このうち、dynamic は @objc が⾃動的に付与されなくなった class MyClass { dynamic func foo() { } // error: 'dynamic' method must be '@objc' @objc dynamic func bar() { } // okay } SE-0160 Limiting @objc inference
  14. NSNumber のキャストがより厳格 に SE-0170 NSNumber bridging and Numeric types _

    = NSNumber(value: 2) as? Bool // nil (Swift 3 は true) _ = NSNumber(value: 1) as? Bool // true _ = NSNumber(value: Int64.max) as? Int32 // nil (Swift 3 は -1)