prevent retain cycle in Swift function pointers

﹥>﹥吖頭↗ 提交于 2019-12-24 03:55:11

问题


How do I prevent a retain cycle when passing around functions as objects in Swift

Imagine you have a datasource object like this

import UIKit
class MagicDataSource:NSObject,UITableViewDatasource {

    deinit {
        println("bye mds")
    }

    //cant use unowned or weak here
    var decorator:((cell:CustomCell)->Void)?

    func tableView(tableView:UITableView,cellForRowAtIndexPath indexPath:NSIndexPath)->UITableViewCell {

        let cell = tableView.dequeueReusableCellWithIdentifier(Identifier, forIndexPath: indexPath) as CustomCell

        decorator?(cell)
        return cell
    }

}

And a view controller like this which has (and wants) a strong ref to that object

import UIKit
class ViewController: UIViewController {

    var datasource:MagicDataSource? = MagicDataSource()

    deinit {
        println("bye ViewCon")
    }

    override func viewDidLoad() {

        super.viewDidLoad()
        datasource?.decorator = decorateThatThing
    }

    func decorateThatThing(cell:CustomCell) {

        //neither of these two are valid             
        //[unowned self] (cell:CustomCell) in
        //[weak self] (cell:CustomCell) in

        cell.theLabel.text = "woot"

    }
}

When you discard the view controller , the datasource will not be released and neither will the view controller as it holds a strong ref to the decorateThatThing function on the view controller.

You can stop the cycle and get the decorator to release by doing this in ViewController but it feels messy

override func viewWillDisappear(animated: Bool) {
    super.viewWillDisappear(animated)
     datasource?.decorator = nil
}

override func viewWillAppear(animated: Bool) {
    super.viewWillAppear(animated)
    datasource?.decorator = decorateThatThing
}

so the question is how do i declare vars and/or functions to avoid having to teardown the datasource manually so that when the view controller is discarded the associated datasource is released too.


回答1:


Rather than

datasource.decorator = decorateThatThing

You can use

datasource.decorator = { [unowned self] cell in
    self.decorateThatThing(cell)
}


来源:https://stackoverflow.com/questions/28137993/prevent-retain-cycle-in-swift-function-pointers

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!