如何将关联类型限制为协议(protocol)。
假设我有以下协议(protocol)和一个实现它的类:
public protocol TestProtocol {
associatedtype TestType
}
public class TestClass<T : NSCoding> : TestProtocol {
public typealias TestType = T
public func get<T>(_ identifier: String) throws -> T? {
return "Test" as? T
}
}
现在一切都很好。 func get 将进行编译,因为编译器知道我的关联类型在这种情况下是一个协议(protocol)。
问题始于这个用例:
public protocol TestProtocol {
associatedtype TestType
func get<T>(_ identifier: String) throws -> T? where T : TestType
}
public class TestClass<T : NSCoding> : TestProtocol {
public typealias TestType = T
public func get<T>(_ identifier: String) throws -> T? {
return "Test" as? T
}
}
这不会编译,因为编译器不知道在这种情况下 TestType 是否是 ProtocolType。
(它说:“类型'T'仅限于非协议(protocol)类型'TestType'”)
如何强制协议(protocol)中的关联类型“TestType”成为协议(protocol)类型?
编辑:我的第一个示例有点误导,我想要实现的目标的更好定义如下
public protocol TestProtocol {
associatedtype TestType
func get<T>(_ identifier: String) throws -> U? where U : TestType
}
public class TestClass<T : NSCoding> : TestProtocol {
public typealias TestType = T
public func get<U>(_ identifier: String) throws -> U? where U : T{
return "Test" as? U
}
}
我希望“get”的返回类型为 U 类型并实现协议(protocol) T(我想用它从我的持久性存储中检索数据)。
问题在于该表示法并不强制 T 是协议(protocol)类型(这会导致编译器错误)。我怎样才能强制执行呢?
第二次编辑:
我研究这个问题的时间越长,我就越确信 Swift-Proposal SE-0142 是这个问题的解决方案(也是 swift 4 的一个功能)。
https://github.com/apple/swift-evolution/blob/master/proposals/0142-associated-types-constraints.md
但是如果您有其他想法如何实现所需的行为,请告诉我;)
最佳答案
正如斯巴罗建议的那样:
public protocol TestProtocol {
associatedtype TestType:Protocol
func get<TestType>(_ identifier: String) throws -> TestType?
}
关于swift - 如何将关联类型约束为协议(protocol),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43829986/