Я пытаюсь написать метод расширения на Dictionary
со следующей подписью:Swift - соответствующий класс динамически
func firstNonNilObjectForKey(keys: [Key], ofClass aClass: Any.Type = String.self) -> Value?
Это должно помочь мне справиться с JSON словарях, где я часто нуждаются в первый непустой но иногда JSON включает в себя null
как значение, которое преобразуется в NSNull
в Cocoa.
Использование было бы что-то вроде:
let dict: [String:AnyObject] = [...]
let myValue = dict.firstNonNilObjectForKey([ "key1", "key2" ]) as? String
Вопрос в том, на реализацию - как соответствовать классу:
if let value = self[key] {
if value is aClass { ... } <--- error: aClass is not a type
if let castedValue = value as? aClass { ... } <--- error: ditto
let type = value.dynamicType
if type == aClass { ... } <--- no error, but doesn't handle subclasses!
// Cannot use value.isKindOfClass() since value may be Any
}
Я думал об альтернативе:
func firstNonNilObjectForKey<ReturnValueType>(keys: [Key]) -> ReturnValueType?
который позволяет быть реализован как
if let value = self[key] as? ReturnValueType { ... }
Но: - Здесь я не могу установить тип по умолчанию (мне в основном нужно String.Type
). - Я не совсем уверен, как ссылаться на это:
let value = dict.firstNonNilObjectForKey([ "key1", "key2" ]) as? String <--- error: Cannot invoke 'firstNonNilObjectForKey' with an argument list of type '([String])'
let value = dict.firstNonNilObjectForKey<String>([ ... ]) <--- error: Cannot explicitly specialize a generic function
Я надеюсь, что это не дубликат, но большинство подобных вопросов здесь просто обращение с ситуацией, когда вы сопрягая против известного класса.
Не будет ли первый метод в альтернативной версии рекурсивным? – jlehr
@jlehr, woops, он делает. Убирай! Спасибо –
Спасибо, это в значительной степени то, что мне нужно ... –