كيفية مقارنة التعداد بالقيم المرتبطة من خلال تجاهل القيمة المرتبطة به في Swift؟




enums comparison (3)

إليك طريقة أكثر بساطة:

enum CardRank {
    case Two
    case Three
    case Four
    case Five
    case Six
    case Seven
    case Eight
    case Nine
    case Ten
    case Jack
    case Queen
    case King
    case Ace

    var isFaceCard: Bool {
        return (self == Jack) || (self == Queen) || (self == King)
    }
}

ليست هناك حاجة إلى زيادة التحميل على عامل التشغيل == ، ولا يتطلب التحقق من نوع البطاقة بناء جملة مربكًا:

let card = CardRank.Jack

if card == CardRank.Jack {
    print("You played a jack")
} else if !card.isFaceCard {
    print("You must play a face card!")
}

بعد قراءة كيفية اختبار مساواة تعداد Swift مع القيم المرتبطة به ، قمت بتطبيق التعداد التالي:

enum CardRank {
    case Number(Int)
    case Jack
    case Queen
    case King
    case Ace
}

func ==(a: CardRank, b: CardRank) -> Bool {
    switch (a, b) {
    case (.Number(let a), .Number(let b))   where a == b: return true
    case (.Jack, .Jack): return true
    case (.Queen, .Queen): return true
    case (.King, .King): return true
    case (.Ace, .Ace): return true
    default: return false
    }
}

يعمل الكود التالي:

let card: CardRank = CardRank.Jack
if card == CardRank.Jack {
    print("You played a jack!")
} else if card == CardRank.Number(2) {
    print("A two cannot be played at this time.")
}

ومع ذلك ، هذا لا يتم تجميع:

let number = CardRank.Number(5)
if number == CardRank.Number {
    print("You must play a face card!")
}

... ويعطي رسالة الخطأ التالية:

لا يمكن تطبيق العامل الثنائي '==' على معاملات النوع 'CardRank' و '(Int) -> CardRank'

أفترض أن هذا بسبب توقعه نوعًا كاملاً ولا يحدد CardRank.Number(2) نوعًا كاملاً ، في حين أن CardRank.Number(2) قام بذلك. ومع ذلك ، في هذه الحالة ، أريدها أن تطابق أي رقم ؛ ليس فقط واحدة محددة.

من الواضح أنه يمكنني استخدام عبارة تبديل ، ولكن الهدف من تنفيذ العامل == هو تجنب هذا الحل المطوّل:

switch number {
case .Number:
    print("You must play a face card!")
default:
    break
}

هل هناك أي طريقة لمقارنة التعداد مع القيم المرتبطة مع تجاهل القيمة المرتبطة به؟

ملاحظة: أدرك أنه يمكنني تغيير الحالة في == الطريقة إلى case (.Number, .Number): return true ، ولكن ، على الرغم من أنه سيعود صحيحًا بشكل صحيح ، إلا أن المقارنة تبدو كما لو كانت تتم مقارنة برقم محدد ( number == CardRank.Number(2) ؛ حيث 2 هي قيمة وهمية) بدلاً من أي رقم ( number == CardRank.Number ).


في Swift 4.2 Equatable سيتم توليفها إذا كانت جميع القيم المرتبطة بها متوافقة مع Equatable . كل ما عليك فعله هو إضافة Equatable .

enum CardRank: Equatable {
    case Number(Int)
    case Jack
    case Queen
    case King
    case Ace
}

https://developer.apple.com/documentation/swift/equatable?changes=_3


تحرير: كما يشير Etan ، يمكنك حذف (_) مطابقة أحرف البدل لاستخدام هذا بشكل أكثر نظافة.

لسوء الحظ ، لا أعتقد أن هناك طريقة أسهل من طريقة switch في Swift 1.2.

في Swift 2 ، ومع ذلك ، يمكنك استخدام مطابقة نمط if-case الجديدة:

let number = CardRank.Number(5)
if case .Number(_) = number {
    // Is a number
} else {
    // Something else
}

إذا كنت تتطلع إلى تجنب الفعل ، فقد تفكر في إضافة خاصية isNumber محسوبة إلى التعداد الخاص بك والتي تنفذ بيان التبديل الخاص بك.





comparison