2016-08-25 19 views
0

我想深入瞭解關閉和分配和使用的機制。閱讀和使用他們,而我已經提出了一些問題,真的吃了我的頭之後:分配給閉包的內存以及它的存儲機制是什麼?

問題 - 1 如何使用封閉的可變不同於普通變量從內存分配點看法?

如:let x:NSString ={}() & let x = NSString()

問題-2 內存分配究竟是如何發生的塊?

請善意解釋這些,以便任何有類似懷疑的讀者可能會從中受益。

**編輯* Shadow對這個問題的回答是對已編輯過的這個問題的另一個方向。

+0

您的文章過於寬泛,而且大家的一些問題已經在這裏找到答案,例如參見http://stackoverflow.com/questions/32693150/whats-wrong-here-instance-member-cannot-be -used-type- – Cristik

+0

@Cristik我編輯了我的問題。你能回答編輯過的問題嗎?謝謝。 –

回答

1

對於具有默認值的存儲屬性或默認關閉內存將立即分配內存,在init方法調用之前。您不能使用self或屬性按默認值定義其他屬性。

您示例中的閉包通常用於此步驟來定義lazy屬性;他們應該是var並標有lazy關鍵字:

懶惰性

內存將在第一屬性調用進行分配。構造{/*...*/}()意味着這個閉包只會在通話時刻執行,並且會返回計算結果(你可以在未命名的函數中看到這個),而不是引用這個閉包。這是非常重要的時刻:你不保留關閉,這個關閉僅分配給執行時刻,並在返回後立即釋放,所以你不需要關心強循環引用問題。

其他的事情 - 當你保存參考關閉:

class myClass { 
    let x: NSString? = nil 
    var closure:() -> NSString = {return "q"} //allocates before class init; deallocates on references release 
    lazy var lazyClosure:() -> NSString = { 
     let z = self.x 
     return z ?? "" 
    }          //allocates on first property call; deallocates on references release 
} 

內存此封分配在同一時間在前面的情況,但他們將繼續生活下去,直到有任何引用。您可以像在不同的對象一樣在這裏查看閉包。循環參考問題可能出現在這裏。 closure沒有捕獲任何東西,所以沒有問題,但lazyClosure捕獲self。如果我們永遠不會撥打lazyClosure就不會有任何問題,因爲這個關閉永遠不會分配。但如果我們將其稱爲它,它將被分配,它將捕獲self,並且會有強循環引用:self指向lazyClosure實例,lazyClosure指向self實例。要解決這個問題,你應該使其中一個引用較弱,你應該使用捕獲列表:在lazyClosure正文中插入[weak self] in[unowned self] in[unowned self] in在我們的情況下,因爲如果屬性叫,那麼self不是nil

lazy var lazyClosure:() -> NSString = { 
    [unowned self] in 
    let z = self.x 
    return z ?? "" 
} 
+0

感謝您的回覆,但是您可以修改您的答案幷包含創建時的塊內存分配與對象之間的區別嗎? –

+0

@ G.Abhisek我修改了答案並糾正了錯誤,請稍後 –

+0

對不起,我很晚纔回復。一個小的澄清 - a)在閉包本身的範圍內聲明的變量是什麼?它們的內存分配是如何發生的? –

相關問題