Создавать объект типа Generic в Swift
Я реализую класс Foo
в Swift, который должен создавать объекты данного подкласса SuperBar
, например. Bar: SuperBar
. Мне очень нравятся generics в Swift, поэтому я попытался реализовать его так:
class Foo<T: SuperBar> {
func instantiateObject() -> T {
return T()
}
}
class SuperBar {
}
class Bar: SuperBar {
}
let foo = Foo<Bar>()
let obj = foo.instantiateObject()
Вы можете запустить фрагмент кода на игровой площадке Xcode и заметить, что obj
имеет тип SuperBar
вместо Bar
, хотя он говорит Bar
, когда я Alt -click на имени константы.
Любые идеи?:)
Ответы
Ответ 1
Если вы добавите required init() { }
в SuperBar
, он будет работать правильно. Это требование всегда должно быть обязательным в любом случае, потому что вы создаете экземпляр из класса переменных.
Тот факт, что он позволяет вам создать его с помощью инициализатора, который не требуется, является ошибкой.
Ответ 2
Отметьте класс init как required
, а затем вызовите init:
class SuperBar {
required init() {
}
}
class Foo<T: SuperBar> {
func instantiateObject() -> T {
return T.init()
}
}
Ответ 3
Вы можете заставить его бросить, если вы точно знаете тип родового.
let emptyObject:T = NSObject() as! T
Очевидно, что это побеждает цель универсального класса, но может быть полезно для некоторых значений по умолчанию или функциональности базового класса, как это было в моем случае.
Это также опасно и сбой, если тип T
не NSObject