如果在swift的extension中override方法,你就會發現這有點難辦

沒故事的卓同學發表於2019-02-19

事情的起因是這樣的:
如果想配置當前vc出現時狀態列的樣式我們可以這樣做:

    override func preferredStatusBarStyle() -> UIStatusBarStyle {
        return .LightContent
    }複製程式碼

有的vc的狀態列是白色,有的是黑色,總這樣override一個方法也是挺礙眼的,那能不能把這個程式碼移進protocol的extension中呢?
這樣的話用起來就像這樣:

    class XxxViewController:UIViewController,LightStatusBarStyle {

    }複製程式碼

想想實現起來很簡單嘛:

protocol LightStatusBarStyle:class {
   func preferredStatusBarStyle() -> UIStatusBarStyle
}

extension LightStatusBarStyle where Self:UIViewController {
    func preferredStatusBarStyle() -> UIStatusBarStyle {
        return .LightContent
    }
}複製程式碼

但是執行起來的時候,你會發現這個方法沒有執行。
於是你再觀察了一下,忽然發覺可能是少了override
我就直接把結果貼出來吧:

你會得到一個error。

extension之前還好好的,怎麼override就不行了呢?
真相到底是什麼?
是Xcode的抽風,是Swift的忽然自我,還是Mac太久沒有重啟?

歡迎進入本期的:

真相就是:

在extension中可以新增新函式,但是不能override一個已有的函式

官方是這麼說的:

Extensions can add new functionality to a type, but they cannot override existing functionality.

總而言之就是:

one more thing

不過我們可以再回憶一下OC的runtime。
可以對方法增加dynamic修飾符宣告為OC的方法,這樣就可以曲線的在extension中使用override了:

class A : NSObject {
    dynamic func doThing() {
        print("dothing super class")
    }
}
class B: A {
}
extension B {
    override func doThing() {
        print("dothing sub class")
        super.doThing()
    }
}複製程式碼

不過這對於我在開始想要直接在extension中直接override UIViewcontroller的方法還是沒有幫助 ┑( ̄Д  ̄)┍

歡迎關注我的微博:@沒故事的卓同學

相關連結:

stackoverflow.com/questions/3…

stackoverflow.com/questions/3…

相關文章