Swift 2 向协议(protocol)添加协议(protocol)一致性

标签 swift protocols swift2

我可以通过 swift 扩展将协议(protocol)一致性添加到协议(protocol)中吗?

//Plain old protocol here
protocol MyData {
    var myDataID: Int { get }
}

我想使 MyData 协议(protocol)默认相等(只需比较 ID)

extension MyData : Equatable { }

但是我得到了这个可爱的错误:

"Extension of protocol 'MyData' cannot have an inheritance clause"

我正在寻找的行为是符合 Equatable(协议(protocol))的 BananaData,因为它实现了 MyData 协议(protocol),该协议(protocol)可以提供 Equatable 的默认实现

//This is the method to implement Equatable
func ==(lhs: MyData, rhs: MyData) -> Bool {
    return lhs.myDataID == rhs.myDataID
}

struct BananaData: MyData {
    var myDataID: Int = 1
}

func checkEquatable(bananaOne: BananaData, bananaTwo: BananaData) {
    //This compiles, verifying that BananaData can be compared
    if bananaOne == bananaTwo { }
    //But BananaData is not convertible to Equatable, which is what I want
    let equatableBanana = bananaOne as Equatable
    //I don't get the additional operations added to Equatable (!=)
    if bananaOne != bananaTwo { } //Error
}

最佳答案

正如错误消息所说:协议(protocol)的扩展不能有继承子句。相反,您可以使 MyData 协议(protocol)继承自原始声明中的 Equatable

protocol MyData: Equatable {
    var myDataID: Int { get }
}

然后您可以为符合 MyData 的类型扩展添加 == 的实现:

func == <T: MyData>(lhs: T, rhs: T) -> Bool {
    return lhs.myDataID == rhs.myDataID
}

但是,我强烈不推荐这样做!如果您向符合类型添加更多属性,则不会检查它们的属性是否相等。举个例子:

struct SomeData: MyData {
    var myDataID: Int
    var myOtherData: String
}

let b1 = SomeData(myDataID: 1, myOtherData: "String1")
let b2 = SomeData(myDataID: 1, myOtherData: "String2")

b1 == b2 // true, although `myOtherData` properties aren't equal.

在上述情况下,您需要为 SomeData 覆盖 == 以获得正确的结果,从而使 == 接受MyData 冗余。

关于Swift 2 向协议(protocol)添加协议(protocol)一致性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31491638/

相关文章:

ios - Swift:如何使用 CLLocationCoordinate2D 将坐标存储为字符串或整数?

从 C 调用 Swift

ios - 更新到 iOS 版本 9.3.3 后,重定向 url 以启动应用程序不起作用

protocols - Mifare 经典 1k 和 NFC 通信协议(protocol)

ios - 如何使用 if 语句将一种类型的变量设置为特定类型的自定义 tableCell?

ios - [NSTaggedPointerString objectAtIndex :]: unrecognized selector sent to instance

ios - UITable DidSelectRowAtIndexPath 未通过 segue 发送数据(意外发现为零)

ios - 如何将 UInt8 数组转换为 Data? ( swift )

ios - MPMoviePlayerViewController 不在 Swift 中播放 .mp4 视频

ios - 在许多 View Controller 上使用委托(delegate)和协议(protocol)快速更改主题