Подтвердить что ты не робот

Использование setValue (значение, forKey: key) в Int? типы запускают метод нестандартного кодирования

Я успешно использую метод setValue(value, forKey: key) в своем подклассе Swift NSObject под NSKeyValueCoding.

Это прекрасно работает с опциями String, например

var name:String?

Однако, на опциях Int, он не работает, вызывая метод ключа undefined, который я переопределил для целей отладки:

override func setValue(value: AnyObject!, forUndefinedKey key: String!) {
    println("\(self) this class is not key value coding-compliant for the key \(key)")
}

Итак, например, ключ myId с хорошим целочисленным значением вызовет метод ключа undefined выше.

var myId:Int?

Если я изменил вышеприведенное определение как необязательное, тогда все работает нормально:

var myId:Int = 0

С myId как факультативным, я пробовал абсолютно все, что я могу себе представить, в способе кастинга, разворачивания, инициализации и т.д. Он просто не видит класс как ключевое значение, совместимое для этих числовых значений.

Я знаю, что это хорошее числовое значение. Изменение объявления var в String? сбои. Он также отлично выглядит в lldb:

Printing description of key:
myId
key NSObject    0x00007fb8d530ca20  0x00007fb8d530ca20
k   NSString    "myId"  0x00007fa2aa942f20
value   __NSCFNumber *  Int64(4348129)  0xb000000004258e13
Printing description of value:
4348129
(lldb) 

Итак, вопрос в том, кто-нибудь использовал - в Swift - метод NSKeyValueCoding setValue(value, forKey: key) для типа Int успешно?

4b9b3361

Ответ 1

KVO не может работать с чистыми опциями Swift, поскольку чистые опции Swift не являются объектами Objective-C. Swift запрещает использование dynamic или @objc с помощью общих классов и структур, потому что нет действительного эквивалента Objective-C, поэтому среда выполнения не настроена для поддержки KVO для экземпляров этих объектов. Что касается того, почему он работает с String?, этот тип не связан с мостом на NSString, поэтому он семантически эквивалентен типу NSString *, Objective-C, который среда выполнения знает о том, как справиться. Но сравните это с Int?, семантический эквивалент которого будет Optional<Int>, а не UnsafePointer<Int> или NSNumber *, как вы могли бы ожидать. На данный момент вам нужно убедить typechecker, что в Objective-C можно безопасно представлять с помощью NSNumber!.

Это полностью назад и, на мой взгляд, неудачное ограничение системы типов. Для любых инженеров, которые сталкиваются с этим сообщением, см. Rdar://18624182.

Ответ 2

Если вы хотите сбросить типы Swift:

var myId:Int?

в

var myId:NSNumber?