2016-10-28 143 views
2

從另一個類創建子類時,需要overrideinit()函數,但不能覆蓋deinit的「函數」。是否可以重寫Swift中的deinit?

這可能在Swift中嗎?

下面是一個例子

class Foo { 
    init(){ 
     print("Foo created") 
    } 

    deinit { 
     print("Foo gone") 
    } 
} 


class Bar: Foo { 

    override init(){ 
     print("Bar created") 
    } 

    //Is not overwritten here 
    deinit { 
     print("Bar gone") 
    } 
} 

例如內部視圖 - 控制

override func viewDidLoad() { 
    super.viewDidLoad() 

    var f: Foo? 
    f = Foo() 
    f = Bar() 
    f = nil 

} 

輸出

Foo created //Foo object initialised - Foo init() called 
Foo created //Foo init() called before calling Bar init()? no call to superclass though.. 
Bar created //Bar object initialised - Bar init() called 
Foo gone  //Foo deinit called as Foo instance replaced by Bar instance 
Bar gone  //Bar deinit called as Bar instance holds no references and is destroyed 
Foo gone  //Foo deinit called again as part of Bar object destruction? 

要添加到我原來的問題一個回合延伸deinit

在該示例代碼似乎重寫init()導致超類的init()函數的調用。這是發生了什麼?

Bar實例取消初始化時會發生相同的行爲。這也是這裏發生的事情嗎?

+5

相關:[瞭解deinitialization和繼承在swift語言](http://stackoverflow.com/questions/24019652/understand-deinitialization-and-inheritance-in-swift-language)。 –

+0

哦哇奇怪我沒有找到這個:/謝謝你的鏈接! – Danoram

+0

控制檯輸出正是我所期望的 - 當f的值被Bar實例覆蓋時,第一個「Foo消失」發生。 Bar的取消分配首先在Bar上調用deinit方法,然後是超類Foo(超類deinit在deinit方法結束時自動調用)。 –

回答

6

deinit是不正常的方法,它不能被覆蓋。每個實例都有一個獨立的deinit它的類及其所有超類的處理程序。

在實例釋放發生之前,會自動調用取消初始化程序。你不能自己打電話給一個deinitializer。超類取消初始化程序由它們的子類繼承,超類取消初始化程序在子類取消初始化程序實現的末尾自動調用。即使子類不提供它自己的去初始化器,也會始終調用超類去初始化器。

絕對沒有理由改變超類在其deinit中做的任何事情。

爲什麼它不同於init?在初始化器中需要傳遞參數,還需要控制執行順序(在super.init(...)之前的一些代碼,在super.init(...)之後的某些代碼)。去初始化是一個具有確定執行順序的自動過程。重寫只能引入不必要的問題。

相關問題