我有一个协议,其中定义了一个函数,函数的返回类型是Superclasstype.
在符合协议的类中,我试图定义此函数,但使用Subclasstype返回类型.
编译器告诉我,这个类不符合协议,因为显然Subclasstype!= Superclasstype
protocol SomeProtocol { func someFunction(someParameter:SomeType) -> Superclasstype? } class SomeClass : SomeProtocol { func someFunction(someParameter:SomeType) -> Subclasstype? { ... } } class Subclasstype : Superclasstype { }
但是,常识告诉我,在这个问题上,Subclasstype应该是Superclasstype的合适替代品.
我究竟做错了什么?
谢谢.
解决方法
在你走得更远之前,我建议在
covariance vs contravariance和
Liskov substitution principle上阅读一些背景资料.
>当子类化是协变时重写的方法的返回类型:方法的子类重写可以返回超类方法的返回类型的子类型.
>通用类型参数是不变的:专业化既不能缩小也不能扩展类型要求.
协议和采用它的具体类型之间的关系更像是泛型而不是子类化,因此协议中声明的返回类型也是不变的. (在第一次阅读时很难确切地说出原因.可能是存在主义与仅限制约束的协议?)
但是,您可以通过指定关联的类型要求来允许协议中的协方差:
protocol SomeProtocol { typealias ReturnType: Superclasstype func someFunction(someParameter: SomeType) -> ReturnType } class SomeClass : SomeProtocol { func someFunction(someParameter: SomeType) -> Subclasstype { /*...*/ } }
现在,很明显,采用SomeProtocol的类型中someFunction的返回类型必须是Superclasstype或其子类型.
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。