Свифт: испытание против опционного значения в случае переключателя


в Swift, как я могу написать случай в операторе switch, который проверяет значение, которое переключается против содержимого дополнительно, пропуская случай, если необязательный содержит nil?

вот как я себе это представляю:

let someValue = 5
let someOptional: Int? = nil

switch someValue {
case someOptional:
    // someOptional is non-nil, and someValue equals the unwrapped contents of someOptional
default:
    // either, someOptional is nil, or someOptional is non-nil but someValue does not equal the unwrapped contents of someOptional
}

если я просто пишу это точно так, компилятор жалуется, что someOptional не развернут, но если я явно разверну его, добавив ! В конце концов, я, конечно, получаю ошибку времени выполнения в любое время someOptional содержит nil. Добавление ? вместо ! будет иметь некоторый смысл для меня (в духе необязательной цепочки, я полагаю), но не делает ошибку компилятора уйти (т. е. фактически не разворачивает необязательный).

2 70

2 ответа:

дополнительно это просто enum такой:

enum Optional<T> : Reflectable, NilLiteralConvertible {
    case None
    case Some(T)

    // ...
}

так что вы можете соответствовать им, как обычно "Связанные Значения" закономерностей:

let someValue = 5
let someOptional: Int? = nil

switch someOptional {
case .Some(someValue):
    println("the value is \(someValue)")
case .Some(let val):
    println("the value is \(val)")
default:
    println("nil")
}

если вы хотите, чтобы совпасть с someValue, используя выражение лица охранника:

switch someValue {
case let val where val == someOptional:
    println(someValue)
default:
    break
}

и для Swift > 2.0

switch someValue {
case let val where val == someOptional:
    print("matched")
default:
    print("didn't match; default")        
}

начиная с Xcode 7 (из бета-версии 1 примечания к выпуску), " новый x? pattern может использоваться для сопоставления шаблонов с опционными в качестве синонима .Some(x)."Это означает, что в Xcode 7 и позже следующий вариант ответ Ринтаро будет работать также:

switch someOptional {
case someValue?:
    print("the value is \(someValue)")
case let val?:
    print("the value is \(val)")
default:
    print("nil")
}