Используйте подкласс как универсальный тип в родительском классе

В моей программе у меня следующая ситуация:

abstract class Loader<T> {
    abstract fun <V> get(ref: T, key: String): V
    abstract fun <V> set(ref: T, key: String, value: V)
}

abstract class ItemHolder {
    companion object {
        private var loader: Loader<*>? = null

        fun <T: Any> getLoader(ref: T): Loader<T> {
            val clsName = ref::class.java.name

            try {
                val opClass = ref::class.java.classLoader!!.loadClass(clsName + "Loader")
                val opCtr = opClass.getConstructor() as Constructor<Loader<T>>
                return opCtr.newInstance()
            } catch (e: ClassNotFoundException) {
                throw RuntimeException("Could not find class ${clsName}Loader. ")
            }
        }
    }

    operator fun <T> set(key: String, value: T) {
        if(loader== null) loader= getLoader(this)
        loader!!.set(this, key, value)
    }

    operator fun <T> get(key: String): T {
       if(loader== null) loader= getLoader(this)
       return loader!!.get(this, key)
    }
}

Класс загрузчика генерируется аннотацией, которую можно использовать на подклассах ItemHolder, Моя проблема сейчас в том, что я хочу использовать подкласс в качестве универсального типа для загрузчика. Это вообще возможно?

Если я использую * как общий тип в объявлении loader Я могу положить в него каждый загрузчик, но не могу вызвать методы с this ссылка. Если я использую Any для этого я могу вызывать методы, но не могу поместить экземпляр любого загрузчика в него. Так, каковы мои другие варианты здесь? Также обратите внимание, что я поместил загрузчик в объект-компаньон, поэтому мне нужно вызывать код отражения только один раз.

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

0 ответов

Другие вопросы по тегам