Определение, если словарь Swift содержит ключ и получает какие-либо его значения

В настоящее время я использую следующие (неуклюжие) фрагменты кода для определения того, содержит ли (непустой) словарь Swift данный ключ и для получения одного (любого) значения из того же словаря.

Как можно сделать это более элегантно в Swift?

// excerpt from method that determines if dict contains key
if let _ = dict[key] {
    return true
}
else {
    return false
}

// excerpt from method that obtains first value from dict
for (_, value) in dict {
    return value
}

Ответ 1

Для этого вам не нужен специальный код, потому что он уже делает словарь. Когда вы получаете dict[key], вы знаете, содержит ли словарь ключ, потому что необязательный, который вы возвращаете, не является nil (и содержит значение).

Итак, если вы просто хотите ответить на вопрос, содержит ли словарь ключ, спросите:

let keyExists = dict[key] != nil

Если вам нужно значение, и вы знаете, что словарь содержит ключ, скажите:

let val = dict[key]!

Но если, как обычно бывает, вы не знаете, что он содержит ключ - вы хотите его извлечь и использовать, но только если он существует - тогда используйте что-то вроде if let:

if let val = dict[key] {
    // now val is not nil and the Optional has been unwrapped, so use it
}

Ответ 2

Почему бы просто не проверить dict.keys.contains(key)? Проверка на dict[key] != nil не будет работать в случаях, когда значение равно нулю. Например, со словарем [String: String?].

Ответ 3

Похоже, вы получили то, что вам нужно от @matt, но если вам нужен быстрый способ получить значение для ключа или просто первое значение, если этот ключ не существует:

extension Dictionary {
    func keyedOrFirstValue(key: Key) -> Value? {
        // if key not found, replace the nil with 
        // the first element of the values collection
        return self[key] ?? first(self.values)
        // note, this is still an optional (because the
        // dictionary could be empty)
    }
}

let d = ["one":"red", "two":"blue"]

d.keyedOrFirstValue("one")  // {Some "red"}
d.keyedOrFirstValue("two")  // {Some "blue"}
d.keyedOrFirstValue("three")  // {Some "red"}

Заметьте, нет гарантий того, что вы на самом деле получите в качестве первого значения, в этом случае просто возвращается "красный".

Ответ 4

Мое решение для реализации кэша, в котором хранится опция NSAttributedString:

public static var attributedMessageTextCache    = [String: NSAttributedString?]()

    if attributedMessageTextCache.index(forKey: "key") != nil
    {
        if let attributedMessageText = TextChatCache.attributedMessageTextCache["key"]
        {
            return attributedMessageText
        }
        return nil
    }

    TextChatCache.attributedMessageTextCache["key"] = .some(.none)
    return nil

Ответ 5

Вот что работает для меня на Swift 3

let _ = (dict[key].map { $0 as? String } ?? "")

Ответ 6

if dictionayTemp["quantity"] != nil
    {

  //write your code
    }