しめ鯖日記

swift, iPhoneアプリ開発, ruby on rails等のTipsや入門記事書いてます

NSNotification.Name.UIApplicationDidBecomeActiveの前半部が省略できる理由

表題の件について調べてみました。
NSNotification.Name.UIApplicationDidBecomeActiveはNotificationに渡す変数で、アプリ立ち上げ時に特定のメソッドを呼びたい時などに利用します。

// アプリがアクティブになった時にtestというメソッドを呼び出す
NotificationCenter.default.addObserver(
            self, selector: #selector(self.test), name: NSNotification.Name.UIApplicationDidBecomeActive, object: nil)

今回はNSNotification.Name.UIApplicationDidBecomeActive.UIApplicationDidBecomeActiveと記述できる理由について調べてみました。

Notification(name: NSNotification.Name.UIApplicationDidBecomeActive)
// ↓ のように省略できる
Notification(name: .UIApplicationDidBecomeActive)

結論としては、UIApplicationDidBecomeActiveがクラス変数な為です。
Swiftでは下のようにクラス変数を省略する事ができます。

let test: MyClass = .Test
class MyClass {
    static let Test = MyClass()
}

Stored PropertyComputed Propertyに置き換えても省略できました。

let test: MyClass = .Test
class MyClass {
    static var Test: MyClass {
        return MyClass()
    }
}

Testという変数の型が違うとエラーになります。

// Member 'Test' in 'MyClass' produces result of type 'Int', but context expects 'MyClass' というエラーになる
let test: MyClass = .Test
class MyClass {
    static var Test: Int {
        return 1
    }
}

型が同じでも、他クラスの変数は使えません。

// これもエラーになる
let test: MyClass = .Test
class MyClass {
}

class MyClass2 {
    static var Test: MyClass {
        return MyClass()
    }
}

staticの代わりにclassを使って変数宣言しても問題なく動きます。

let test: MyClass = .Test
class MyClass {
    class var Test: MyClass {
        return MyClass()
    }
}

enumやstructでも同じような挙動になりました。

let test1: MyEnum = .Test
enum MyEnum {
    case test
    
    static var Test: MyEnum {
        return .test
    }
}

let test2: MyStruct = .Test
struct MyStruct {
    static var Test: MyStruct {
        return MyStruct()
    }
}