关联类型为 : how to use in an abstract method? 的 Swift 协议(protocol)

标签 swift protocols associated-types

我有两种协议(protocol),一种用于 ViewModel,一种用于将 ViewModel 类型作为关联类型的 ConfigurableView。

public protocol ViewModel {}

public protocol ConfigurableView {

  associatedtype ViewModelType: ViewModel

  func configure(with viewModel: ViewModelType)

}

在我用抽象模型配置抽象 View 的方法中:

let viewModel = getMyViewModel() // returns ViewModel

if let configurableView = cell as? ConfigurableView {
    configurableView.configure(with: viewModel)
}

我收到“协议(protocol)‘ConfigurableView’只能用作通用约束,因为它具有自身或相关类型要求”。

如果它是一个 ConfigurableView 实例,我如何告诉编译器我想用这个实例具有的任何关联类型配置 View ?

最佳答案

我实际上找到了一个我认为不错的解决方案,它不需要对我的架构进行太多改动。感谢@lib 让我走上了正确的道路。诀窍是让上面的协议(protocol)没有 associatedType 要求,并带有将通用 ViewModel 转换为特定 View 模型的 associatedType 的扩展。我相信这是类型删除?但它看起来不像我读过的任何例子。

public protocol ViewModel {}

/*
 This parent protocol exists so callers can call configure on
 a ConfigurableView they don't know the specific type of.
*/
public protocol AnyConfigurableView {

  func configure(with anyViewModel: ViewModel)

}

public protocol ConfigurableView: AnyConfigurableView {

  associatedtype ViewModelType: ViewModel

  func configure(with viewModel: ViewModelType)

}

/*
 This extension does the trick of converting from the generic
 form of ConfigurableView to the specific form.
 */
public extension ConfigurableView {

  func configure(with anyViewModel: ViewModel) {

    guard let viewModel = anyViewModel as? ViewModelType else {
      return
    }

    configure(with: viewModel)

  }

}

用法:

let viewModel = getViewModel()
(someView as? AnyConfigurableView)?.configure(with: viewModel)

关于关联类型为 : how to use in an abstract method? 的 Swift 协议(protocol),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52919034/

相关文章:

ios - 有没有办法在 Swift 中将特殊字符转换为普通字符?

python - 我在哪里可以找到所有窗口管理器协议(protocol)原子的列表?

rust - 有没有办法让一个特征在它扩展的另一个特征中为关联类型指定自己?

ios - 使用核心数据swift ios将实体的所有属性获取到tableview中行中的标签

swift - 结束刷新时更改 tableView 内容插入?

swift - 对返回类强制执行通用协议(protocol)约束

ios - 扩展符合 NSFetchRequestResult 的协议(protocol)

ios - 类型 X 不继承自 Y

Swift Self 作为关联类型绑定(bind)在协议(protocol)中

swift - 何时不使用 eraseToAnyPublisher()