You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift MVVM使用协议处理ViewModel事件报错解决方案咨询

解决MVVM代理模式中的初始化类型不匹配问题

这个问题我之前开发MVVM的时候也踩过坑!咱们先搞清楚报错的根源:你在SecondViewController的属性定义里直接写let viewModel = SecondViewModel(del: self),这时候ViewController的实例还没有完成初始化流程,self在这里的类型并不是SecondViewController实例,而是一个构造闭包类型(SecondViewController) -> () -> SecondViewController,自然不符合SecondViewModelEvents协议的要求,所以才会抛出类型不匹配的错误。

下面给你两种常用的正确实现方式:

方式一:使用lazy var延迟初始化ViewModel

lazy属性的特点是第一次被访问时才会初始化,这时候ViewController已经完成实例化,self就是合法的协议遵守者实例了:

class SecondViewController: UIViewController, SecondViewModelEvents {
    // 用lazy var替代let,确保初始化时self已完全创建
    lazy var viewModel = SecondViewModel(del: self)

    @IBAction func buttonPressed(_ sender: Any) {
        self.viewModel.loadDataFromServer()
    }

    func changeBackground() {
        self.view.backgroundColor = UIColor.red
    }
}

方式二:在viewDidLoad中初始化ViewModel

ViewController的viewDidLoad方法会在视图加载完成后调用,这时候实例已经完全初始化,self的类型完全符合要求:

class SecondViewController: UIViewController, SecondViewModelEvents {
    // 先声明为隐式解包可选类型,后续赋值
    var viewModel: SecondViewModel!

    override func viewDidLoad() {
        super.viewDidLoad()
        // 这里self已经是合法的SecondViewController实例
        viewModel = SecondViewModel(del: self)
    }

    @IBAction func buttonPressed(_ sender: Any) {
        self.viewModel.loadDataFromServer()
    }

    func changeBackground() {
        self.view.backgroundColor = UIColor.red
    }
}

额外优化:避免循环引用

这里还要提醒你一个容易忽略的点:当前的代码存在循环引用风险——SecondViewController持有viewModel,而viewModel的events属性又持有SecondViewController,会导致两者都无法被释放。解决方法是给协议添加类约束,并把events声明为weak:

// 给协议添加AnyObject约束,确保只有类能遵守
protocol SecondViewModelEvents: AnyObject {
    func changeBackground()
}

class SecondViewModel: NSObject {
    // 用weak修饰代理属性,打破循环引用
    weak var events: SecondViewModelEvents?

    init(del: SecondViewModelEvents) {
        self.events = del
    }

    func loadDataFromServer() {
        self.events?.changeBackground()
    }
}

这样整个MVVM代理模式的实现就既正确又安全啦!

内容的提问来源于stack exchange,提问作者yildirimatcioglu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.12 05:32:10