Kotlin Generic Inheritence, как приводить наследуемый объект - PullRequest
1 голос
/ 12 октября 2019

У меня есть следующий случай.

Базовый класс для моего объекта.

abstract class A{
  lateinit var x: Animal
  fun defineStuff() {
    x = Factory().createFor(getAnimalType())
  }
  abstract fun <T: Animal> getAnimalType(): Class<T>
}

У меня и Животное, и Собака определены так:

open class Animal
class Dog : Animal()

Фабрикакласс предоставляется для меня моей рамкой. это подпись:

fun <T: Animal> createFor(animalType: Class<T>): T

и теперь я создал следующий класс:

class B : A() {

  override fun <T: Animal> getAnimalType(): Class<T> {
      return Dog::class.java as Class<T>
  }
}

следующая строка выделена моим линтером как "Непроверенный класс"

Значит ли это, что я делаю что-то не так? Есть ли лучший способ использовать дженерики в Kotlin, которые не будут выдавать предупреждение? или я должен просто игнорировать это.

Ответы [ 2 ]

2 голосов
/ 12 октября 2019

На самом деле, на мой взгляд, лучшее решение A должно быть универсальным (поскольку A является абстрактным, и одна из довольно важных вещей - это тип упакованного значения). Затем вы можете сделать следующее:

abstract class A<T: Animal> {
    lateinit var x: T
    fun defineStuff() {
        x = Factory().createFor(getAnimalType())
    }
    abstract fun getAnimalType(): Class<T>
}

class DogA: A<Dog>() {
    override fun getAnimalType() = Dog::class.java
}
2 голосов
/ 12 октября 2019

Тип действительно стирается во время выполнения. Вот о чем предупреждение.

Вызывающий код может сделать это:

val b: B = B()
val catClass: Class<Cat> = b.getAnimalType()

Компилятор разрешит это. Код будет выполняться без исключения.

Ваша базовая функция не должна быть универсальной, вместо этого она должна иметь тип возвращаемого значения Class<out Animal>.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...