LoginSignup
1

More than 1 year has passed since last update.

posted at

updated at

生成しないenum

Qiita Advent Calendar 2020 Swift 2日目のエントリーです。

1日目「Swiftに搭載予定のC++相互運用機能」 は、
C++コードをSwiftコードとして呼び出せるようになる夢のような話でした。
ますますSwiftの時代ですね。

書いたこと

case値を持たないenumは生成することが出来ません。
その特性を利用して、enumは以下のような使い方も出来ます。

  • 名前空間としてのenum
  • 演算子の型を表すenum

名前空間としてのenum

SwiftはObjective-C同様、名前空間は正式サポートされていませんが、標準スタンダードライブラリーで用意されているUnicodeのようにUtility的な機能や定数をまとめる際に、名前空間としてenumが使用されます。

enum内部では以下の宣言が出来ます。

  • typealias
  • struct / enum / class
  • static let / static var / static func

使い所としては、以下のような場面が想定されます。

  • 定数をまとめる
  • Utility的な機能をまとめる

例1: 定数をまとめる

enumで定数をまとめる.swift
enum 👮 {
    static let name = "Mike"
    static let age = 32
    static let gender = 0
}
print(👮.name);

例2: Utility的な関数をまとめる

enumでUtility的な関数をまとめる.swift
enum Qiita {
    // URLを返す
    static func commentURL(_ commentId: String) -> URL {
        return URL(string: "\(scheme)://\(host)/\(Path.comments)/\(commentId)")!
    }

    // 定数をまとめる
    private static let scheme = "https"
    private static let host = "qiita"
    private enum Path {
        static let comments = "comments"
        static let users = "users"
        static let tags = "tags"
    }
}


print(Qiita.commentURL("14159265359"))

演算子の型定義

Arrayの添字に、...演算子を渡すことが出来ます。

Arrayはカスタムな演算子を添え字に渡せる.swift
let fruits = ["🍎", "🍌", "🍊", "🍐", "🍉"]
let sliced = fruits[...] // ArraySlice<String>  ["🍎", "🍌", "🍊", "🍐", "🍉"]

これは以下のようにメソッドが定義されているためです。

array.swift
subscript(x: (UnboundedRange_) -> ()) -> ArraySlice<Element> { get set }

このUnboundedRange_がenumです。

UnboundedRange_.swift
public enum UnboundedRange_ {
  public static postfix func ... (_: UnboundedRange_) -> () {
    fatalError("uncallable")
  }
}

UnboundedRange_内で、(UnboundedRange_) -> ()型が返すカスタム演算子...が定義されています。

これによって(UnboundedRange_) -> ()で宣言された引数に、...演算子を渡すことが出来ます。

まとめ

正式に名前空間がサポートされているC++、C#、PHPでは、名前空間を省略するための機能も用意されています。
(C++,C#ならば、using、PHPならば、use)

Swiftではどちらかというと上記の役割はモジュールが担っているところがあり、複雑になりかねないためサポートに踏み切れない理由がありそうです。

参照

以下の記事をまとめました。

https://qiita.com/takasek/items/3497188559fbf717751b
→ 「なぜ名前空間としてenumが使われるのか」について詳細に解説されています。

https://qiita.com/ysn/items/29363f0f6cc78d1d6561
→ カスタムの演算子の型の作り方を解説しています。

https://qiita.com/YOCKOW/items/dd409b9588f4be72f58f
→ UnboundedRange_型についてはこちらで詳しく解説されています。Array[...]の存在はこちらの記事でしりました。

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
What you can do with signing up
1