【发布时间】:2016-08-12 16:09:24
【问题描述】:
我不得不在 Swift 中使用类型擦除几次,但它总是涉及到一个通用协议。在这种情况下,它涉及通用枚举和和通用协议,我很难过。
这是我的通用枚举和带有必要扩展的通用协议:
enum UIState<T> {
case Loading
case Success([T])
case Failure(ErrorType)
}
protocol ModelsDelegate: class {
associatedtype Model
var state: UIState<[Model]> { get set }
}
extension ModelsDelegate {
func getNewState(state: UIState<[Model]>) -> UIState<[Model]> {
return state
}
func setNewState(models: UIState<[Model]>) {
state = models
}
}
这是我的类型擦除泛型类:
class AnyModelsDelegate<T>: ModelsDelegate {
var state: UIState<[T]> {
get { return _getNewState(UIState<[T]>) } // Error #1
set { _setNewState(newValue) }
}
private let _getNewState: ((UIState<[T]>) -> UIState<[T]>)
private let _setNewState: (UIState<[T]> -> Void)
required init<U: ModelsDelegate where U.Model == T>(_ models: U) {
_getNewState = models.getNewState
_setNewState = models.setNewState
}
}
我收到以下错误(它们已在代码示例中标记):
错误 #1:
Cannot convert value of type '(UIState<[T]>).Type' (aka 'UIState<Array<T>>.Type') to expected argument type 'UIState<[_]>' (aka 'UIState<Array<_>>')
我已经为此工作了一段时间,并且该代码有很多“几乎可以工作”的变体。错误总是与getter有关。
【问题讨论】:
-
您将一个类型传递给一个采用该类型实例的方法
-
我有点困惑,为什么你的
getNewState函数需要输入,肯定应该是() -> UIState<[Model]>?虽然如果您的getNewState和setNewState函数仅用于将获取和设置转发到您的类型擦除,它们不是必需的,因为您可以直接在带有闭包的类型擦除中执行此操作(即_getNewState = { models.state }和 @987654329 @)。 -
是的,我对此也有点困惑 :)。它需要输入,因为最初我在没有输入时遇到错误。让我尝试重构。
-
谢谢,就是这样。请发表您的答案。
标签: ios swift generics swift2 swift-protocols