[英]Swift protocol with associated type and shadow type erasure
我需要将实现具有关联类型的协议的对象传递给接受协议的方法。 这在Swift(最新的Swift 5)中是不可能的,因此我在此Blog的影子协议中使用了类型擦除。
protocol ShadowA {
func test(data: Any) -> String
}
extension ShadowA {
func test(data: Any) -> String {
return "shadow"
}
}
protocol A: ShadowA {
associatedtype AT
func test(data: AT) -> String
}
class SpecificA: A {
typealias AT = Int
func test(data: Int) -> String {
return "specific"
}
}
问题是,当我将对象传递给方法时,将调用“阴影的默认实现”,而不是“通用”实现。 您可以检查操场上看到的情况。
是否有问题或在Swift中根本无法使用该用例?
此动态分派和直接分派Magic进一步说明了有关检查此swift-method-dispatch的信息
动态调度是选择在运行时调用哪种多态操作(方法或函数)的实现的过程。
在protocol extension
中实现的任何方法都是直接分派的
我会解释更多
因为ShadowA
是protocol
并且在扩展中具有default implementation
,所以编译器会想到以下提示:“ Any class can adopt to this protocol without implement this method because it have default implementation
”
直接派遣
所以在这一行,编译器从item了解test(data:Any)
,因为item是具有默认实现的协议,所以它将其定向为调用默认默认实现
return "in method: \(item.test(data: 0))"
func passedIntoMethod(item: ShadowA) -> String {
return "in method: \(item.test(data: 0))"
}
也在这条线上
let a2: ShadowA = SpecificA() // becuse compiler know only about a2 at this line that it is Protocol so it direct dispatch it
print(a2.test(data: 0))
动态调度
在这里,编译器知道a1是concreate类型,因此它调用在其内部实现的test Method。 如果没有实现,它将调用默认实现
let a1 = SpecificA()
print(a1.test(data: 0))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.