Ссылка на внутренний тип Generics - PullRequest
0 голосов
/ 25 января 2019

Можно ли извлечь внутренние универсальные типы?

Представьте себе следующие классы:

interface Animal { }

class Bear implements Animal { }

class AnimalRule<ANIMAL extends Animal> { }

class BearRule extends AnimalRule<Bear> { }

Теперь я хочу написать тесты для этого кода, но я хочу иметь универсальную базуtest class.

Я могу объявить это так:

class AnimalRuleAltTest<ANIMAL extends Animal, RULE extends AnimalRule<ANIMAL>> {
  RULE rule;
  ANIMAL animal;
}

class BearRuleAltTest extends AnimalRuleAltTest<Bear, BearRule> { }

Однако я должен пропустить и Bear, и BearRule, что кажется излишним, поскольку компилятор наверняка знает, что BearRuleуже реализует AnimalRule< Медведь >.


Можно ли каким-то образом извлечь внутренний универсальный тип, если я предоставлю только класс правил?

Примерно так:

class AnimalRuleTest<RULE extends AnimalRule<ANIMAL>> {
  RULE rule;
  ANIMAL animal;
}

class BearRuleTest extends AnimalRuleTest<BearRule> { }

Обновление: Просто чтобы прояснить, я спрашиваю о извлечении внутренних классов / возможно ли это, а не о том, как это исправить.

Ответы [ 2 ]

0 голосов
/ 25 января 2019

Этот фрагмент кода, следуя той же структуре, что и вы, идет от BearRuleTest, чтобы получить Bear.

public static void main(String...strings) throws Exception {

        final ParameterizedType bearRuleTestGenericSuperclass =
            (ParameterizedType) BearRuleTest.class.getGenericSuperclass();
        final Type type = bearRuleTestGenericSuperclass.getActualTypeArguments()[0];
        final ParameterizedType animalRuleGenericSuperclass =
            (ParameterizedType) Class.forName(type.getTypeName()).getGenericSuperclass();

        System.out.println(
            animalRuleGenericSuperclass.getActualTypeArguments()[0]
        );
    }

edit:

  • Сначала я получаю универсальный суперкласс вашего ruleTest, который равен AnimalRuleTest с AnimalRule.
  • Затем я получаю первый аргумент, который BearRule.
  • Iзагрузить из загрузчика классов класс BearRule, затем получить его genericSuperclass, который равен AnimalRule с универсальным параметром.
  • Затем я беру первый аргумент, который является Bear.
0 голосов
/ 25 января 2019

Попробуйте это:

class AnimalRuleAltTest<ANIMAL extends Animal> {
    AnimalRule<ANIMAL> rule;
    ANIMAL animal;
}

class BearRuleAltTest extends AnimalRuleAltTest<Bear> { }

Кроме того, замените все вхождения RULE в AnimalRuleAltTest на AnimalRule<ANIMAL>.

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