Я действительно смутился, обнаружив, что следующий код просто отказывается сбой с типичным исключением "Неожиданно найденное ноль при распаковке необязательного значения", которое вы ожидаете от разворачивания силы bar.
struct Foo {
var bar: Bar?
}
struct Bar {}
var foo = Foo()
debugPrint(foo.bar) // nil
debugPrint(foo.bar!.dynamicType) // _dynamicType.Bar
Кажется, что dynamicType как-то может отступить к определенному типу bar - без сбоев.
Обратите внимание, что это происходит только тогда, когда bar определяется как тип значения (поскольку @dfri говорит), Foo является struct или final class (как отмеченный @MartinR) и Foo изменен.
Вначале я считал, что это может быть просто оптимизация компилятора из-за того, что тип bar известен во время компиляции, поэтому разворот силы мог быть оптимизирован - но он также падает, когда bar определяется как final class. Кроме того, если я устанавливаю "Уровень оптимизации" на -Onone, он все равно работает.
Я склонен думать, что это странная ошибка, но хотел бы получить подтверждение.
Является ли это ошибкой или функцией с dynamicType, или я просто что-то пропустил здесь?
(Использование Xcode 7.3 w/Swift 2.2)
Обновление Swift 4.0.3
Это все еще воспроизводимо (с еще более минимальным примером) в Swift 4.0.3:
var foo: String?
print(type(of: foo!)) // String
Здесь мы используем преемник dynamicType, type(of:), чтобы получить динамический тип; и, как и в предыдущем примере, он не сбой.