Доступ к аргументам типа из универсальных типов, используемых в привязках типов

Я обнаружил следующие проблемы с дженериками. Рассмотрим универсальный интерфейс

public interface A<X> {
    X get();
    void doStuff(X x);
}

Теперь предположим следующее определение метода:

public <T extends A<?>> void foo(T t) {
    bar(t);
}

Из-за подстановочного знака информация о типе для возвращаемого типа get () недостаточна. Следовательно, я должен делегировать другому методу, который «привязывает» этот подстановочный знак к переменной нового типа:

private <X> void bar(A<X> t) {
    X x = t.get();
    t.doStuff(x);
}

Вызов bar () в foo не разрешен, компилятор выводит следующее сообщение об ошибке:

Метод bar (A) в тесте типа не применимо для аргументов (T)

Однако, если я изменю метод foo () на

public <T extends A<?>> void foo(T t) {
    A<?> u = t; // No explicit cast required, no "unchecked" warning!
    bar(u);
}

, он работает.Почему? Это ошибка компилятора? Будем очень признательны за любые комментарии по этому поводу.

Примечания:

  • Причина, по которой я просто не объявляю метод foo как void foo (A), заключается в том, что я фактически использую верхнее ограничение типа interesection (&).
  • Причина, по которой я не объявляю X как переменную типа в foo (), заключается в том, что у меня действительно есть проблема на уровне класса, и я не хочу без необходимости увеличивать количество параметров типа этого класса.
5
задан misberner 18 November 2011 в 16:17
поделиться