【发布时间】:2017-03-07 17:25:30
【问题描述】:
我有一个 Swift 3 项目,我在其中声明了一个具有如下关联类型的协议:
protocol ViewModelContainer {
associatedtype ViewModelType
var viewModel: ViewModelType! { get set }
}
我想检查两个对象是否实现 ViewModelContainer 并且它的关联类型 ViewModelType 以“通用”方式进行分配。
理想情况下,我想做这样的事情:
if let container = container as? ViewModelContainer, let model = model as? container.ViewModelType {
container.viewModel = model
}
但我不能将container 转换为ViewModelContainer:
Protocol 'ViewModelContainer' 只能用作通用约束,因为它具有 Self 或关联的类型要求
我目前的解决方法是直接回退到特定类及其关联类型,但这会使我的代码非常冗长且容易出错:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if let vc = segue.destination as? MediaPlaySelectionViewController, let vm = sender as? MediaPlaySelectionViewModel {
vc.viewModel = vm
}
if let vc = segue.destination as? SearchResultsViewController, let vm = sender as? SearchResultsViewModel {
vc.viewModel = vm
}
if let vc = segue.destination as? ReviewDetailsViewController, let vm = sender as? ReviewDetailsViewModel {
vc.viewModel = vm
}
if let vc = segue.destination as? ReviewComposerViewController, let vm = sender as? ReviewComposerViewModel {
vc.viewModel = vm
}
}
我尝试使用通用 UIViewControllers,但因为 Objective-C doesn't recognize generic Swift classes 而卡住了,因此无法在 Storyboard 中使用。
【问题讨论】:
-
这真的很愚蠢...但是如果您创建一个空协议,然后使所有符合
ViewModelContainer的类型都符合该协议,那么您检查是否符合该协议而不会碰到这个问题。 -
我想真正的问题是为什么
container不是静态类型化为符合ViewModelContainer的类型?您可能正在寻找一种类型橡皮擦。 -
为什么不将
ViewModelType作为协议? -
@Hamish UIKit 讨厌泛型,我不得不在某些时候使用
Any来解决它 -
@dichen 我已经有一个
ViewModel协议。但这在这里没有帮助,因为每个容器都必须包含其特定的视图模型类。
标签: swift swift-protocols associated-types