Swiftのweakとunowned」

3094 ワード

作者:Thomas Hanning,原文リンク,原文日付:2015-11-30訳者:pmst;校正:Cee;下書き:Cee
weakとunownedキーワードを使用すると、いわゆるループ参照を避けることができます.この文章では、両者の違いについて議論します.

循環参照とは?


私は「A Trick To Discover Retain Cycles」ブログでメモリ管理の重要性を強調しました.ARCがあなたのために苦労しても.
まず、RootViewControllerSecondViewControllerの2つのビューコントローラを作成します.RootViewControllerビューのボタンをクリックすると、SecondViewControllerが表示されます.storyboardでsegueを使用することで、この目的を簡単に実現することができます.また、ModelObjectという名前のクラスを作成しました.ModelObjectDelegateのタイプの委任オブジェクトが含まれています(このオブジェクトはModelObjectDelegateプロトコルに従っているとも言えます).SecondViewControllerのビューのロードが完了すると、現在のビューコントローラは、ModelObjectのエージェントに自分を任命します.

// ModelObject  
import Foundation
 
protocol ModelObjectDelegate: class {
    
}
 
class ModelObject {
    
    var delegate: ModelObjectDelegate?
       
}


// SecondViewController  
import UIKit
 
class SecondViewController: UIViewController, ModelObjectDelegate {
    
    var modelObject: ModelObject?
    
    override func viewDidLoad() {
        super.viewDidLoad()
        modelObject = ModelObject()
        modelObject!.delegate = self
    }
        
    @IBAction func closeButtonPressed(sender: UIButton) {
        dismissViewControllerAnimated(true, completion: nil)
    }
    
}

準備が完了したら、メモリ管理をテストします.まず、SecondViewControllerビューコントローラを解放します.メモリの使用量が低下していないことがわかります.これはなぜですか.SecondViewControllerオブジェクトが解放され、メモリが解放されることが望ましい.まず、オブジェクト間の関係を理解しましょう.SecondViewControllerのロードが完了すると、オブジェクト間の関係は次のようになります.SecondViewControllerを解放しました
図に示すように、RootViewControllerSecondViewControllerに対して強い参照関係を持たなくなった.しかし、SecondViewControllerModelObjectのオブジェクトの間には常に相互に強い参照が保たれている.だから解放されません

Weak


このような状況を回避するために、ARCがメモリを解放することを阻止しないweakとして参照関係を宣言することができます.

import Foundation
 
protocol ModelObjectDelegate: class {
    
}
 
class ModelObject {
    
    weak var delegate: ModelObjectDelegate?
    
}

オブジェクトリレーションシップマップは次のように表示されます.SecondViewControllerオブジェクトとModelObjectオブジェクトの間には強い参照関係が1つしか残っていないため、メモリの解放に成功することは間違いありません.

Unowned


また、unownedのキーワードを使ってweakを置き換えることもできますが、両者の違いはどこですか?weakを使用する場合、属性はオプションのタイプであり、nilの値が許容される場合があります.一方、unownedを使用する場合は、オプションのタイプに設定することはできません.unownedプロパティはオプションのタイプではないため、initメソッドで値を初期化する必要があります.

import Foundation
 
protocol ModelObjectDelegate: class {
    
}
 
class ModelObject {
    // :swift  
    //          nil
    unowned var delegate: ModelObjectDelegate
    
    init(delegate:ModelObjectDelegate) {
        self.delegate = delegate
    }
        
}

属性がオプションのタイプかどうかによって、weakunownedの間で選択できます.

リファレンス


A Trick To Discover Retain Cycles Optionals In Swift Swift Programming Series (iBook Store)
本文はSwiftGG翻訳グループから翻訳して、すでに作者の翻訳の授権を得て、最新の文章は訪問して下さいhttp://swift.gg.