Java два уровня дженериков странное поведение - PullRequest
1 голос
/ 25 апреля 2020

У меня есть следующие логики c


public class Why {

    public static void main(String[] args) {
        Gen<A> gen = new Gen<>();
        gen.m(new A()); //eeeeeeeeee A
    }
}

class A {}

class B extends A {}

class C extends A {}

class Gen<E> {
    Test test = new Test();

    public void m(E e) {
        test.test(e);
    }
}

class Test {

    public <E extends A> void test(E e) {
        System.out.println("XXXXXXXXXX " + e.getClass().getSimpleName());
    }

    public <E> void test(E e) {
        System.out.println("eeeeeeeeee " + e.getClass().getSimpleName());
    }

}

вывод для main означает, что компилятор выбирает второй метод в Test, это странно или я что-то пропустил? не должен java знать фактический класс для теста Gen #?

1 Ответ

4 голосов
/ 25 апреля 2020

Разрешение перегрузки метода происходит во время компиляции.

Когда компилятор компилирует Gen<E>, он ничего не знает о E, то есть он не может гарантировать, что E расширяет A поэтому он должен вызвать перегрузку test с <E>.

Если вы удалите эту перегрузку test(), вы получите ошибку компиляции, так как другая вообще не совместима :
The method test(E extends A) in the type Test is not applicable for the arguments (E)

Чтобы он вызывал другого, измените на Gen<E extends A>.

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