【问题标题】:Extend Int enum with comparison operators使用比较运算符扩展 Int 枚举
【发布时间】:2017-11-23 23:23:23
【问题描述】:

你经常有这样的 Int 枚举:

enum Difficulty: Int {
    case Easy = 0
    case Normal
    case Hard
}

Difficulty 值有一定的含义,我们可能想为它们引入顺序。例如,我们需要比较的地方:

let isBonusAvailable = level.difficulty.rawVAlue <= Difficulty.Hard.rawValue

我想让这段代码更短一点:

let isBonusAvailable = level.difficulty <= .Hard

如果我将&lt;= 直接添加到Difficulty,它可以轻松实现。但是我想总体上解决这个问题,所以我尝试了这个超级棘手的方法:

protocol RawRepresentableByInt {
    var rawValue: Int { get }
}

extension RawRepresentableByInt {
    static func <(lhs: RawRepresentableByInt, rhs: RawRepresentableByInt) -> Bool {
        return lhs.rawValue < rhs.rawValue
    }

    static func >(lhs: RawRepresentableByInt, rhs: RawRepresentableByInt) -> Bool {
        return lhs.rawValue > rhs.rawValue
    }

    static func <=(lhs: RawRepresentableByInt, rhs: RawRepresentableByInt) -> Bool {
        return lhs.rawValue <= rhs.rawValue
    }

    static func >=(lhs: RawRepresentableByInt, rhs: RawRepresentableByInt) -> Bool {
        return lhs.rawValue >= rhs.rawValue
    }
}

// Error: Extension of protocol 'RawRepresentable' cannot have an inheritance clause
extension RawRepresentable: RawRepresentableByInt where RawValue == Int  {
}

它会产生编译器错误:

错误:协议“RawRepresentable”的扩展不能有继承子句

我认为在逻辑上与Int enum 相比没有什么不可实现的。请帮我欺骗 Swift 编译器。任何也需要此类扩展的人都可以参与。

【问题讨论】:

    标签: swift enums integer compare extension-methods


    【解决方案1】:

    这比我想象的要容易。所以,基本上你可以使用Self 而不是创建额外的协议。

    enum Difficulty: Int {
        case Easy = 0
        case Normal
        case Hard
    }
    
    extension RawRepresentable where RawValue: Comparable {
        static func <(lhs: Self, rhs: Self) -> Bool {
            return lhs.rawValue < rhs.rawValue
        }
    
        static func >(lhs: Self, rhs: Self) -> Bool {
            return lhs.rawValue > rhs.rawValue
        }
    
        static func <=(lhs: Self, rhs: Self) -> Bool {
            return lhs.rawValue <= rhs.rawValue
        }
    
        static func >=(lhs: Self, rhs: Self) -> Bool {
            return lhs.rawValue >= rhs.rawValue
        }
    }
    
    let easy = Difficulty.Easy
    print(easy > .Hard) // false
    

    【讨论】:

    • 您可以使用where RawValue: Comparable 而不是where RawValue == Int,从而为所有Comparable 原始类型(包括Int)自动生成比较运算符。
    • Comparable 很好,谢谢。但是在这种情况下自动生成不起作用,因为可比较的是RawValue,而不是枚举。
    猜你喜欢
    • 1970-01-01
    • 2021-04-06
    • 1970-01-01
    • 2021-06-08
    • 2018-12-23
    • 1970-01-01
    • 2020-11-10
    • 2011-01-28
    • 2022-11-11
    相关资源
    最近更新 更多