如何将Swift协议与通用方法和通用类型一起使用

时间:2016-12-07 14:33:15

标签: swift generics swift-protocols

我有一个班级StateMachine<A>

final class StateMachine<A> {

    private var previousState: State? = nil
    private var currentState: State
    private var content: A?
    var delegate: StateMachineDelegate?
    var state: State = .loading {
        didSet {
            previousState = currentState
            currentState = state
        }
    }

    init(currentState: State, delegate: StateMachineDelegate?) {
        self.currentState = currentState
    }
}

和代表协议StateMachineDelegate

protocol StateMachineDelegate {
    func updateWith(content: A)
}  

我试图表达如果使用类型A创建StateMachine,委托应该实现接受相同类型A的参数的方法func updateWith(content: A)。这可能吗?

1 个答案:

答案 0 :(得分:2)

您可以通过添加其他类型参数来实现您所要求的内容:

final class StateMachine<A, Delegate: StateMachineDelegate> where Delegate.A == A {

    private var previousState: State? = nil
    private var currentState: State
    private var content: A?
    var delegate: Delegate?
    var state: State = .loading {
        didSet {
            previousState = currentState
            currentState = state
            delegate?.updateWith(content: state)
        }
    }

    init(currentState: State, delegate: Delegate?) {
        self.currentState = currentState
    }
}

protocol StateMachineDelegate {
    associatedtype A
    func updateWith(content: A)
}

但我不会这样做。如果你的委托真的只是一个更新方法,那么闭包是一个更好的解决方案:

final class StateMachine<A> {    
    // ...
    private var content: A?
    var notify: (A) -> Void

    var state: State = .loading {
        didSet {
            previousState = currentState
            currentState = state
            notify(state)
        }
    }

    init(currentState: State, notify: @escaping (A) -> Void) {
        self.currentState = currentState
        self.notify = notify
    }
}