Границы дженериков Java с параметрами рекурсивного типа

У меня есть базовый класс Thing, который предоставляет некоторые базовые функции, включая получение ссылки на ThingInfoс параметром типа типа подкласса Thing. Поскольку в Java нет собственных типов, я не могу использовать это для параметра типа для возвращаемого значения ThingInfo, поэтому Thingдолжен принимать параметр рекурсивного типа, чтобы мы могли вернуть правильный параметризованный ThingInfo.

interface ThingInfo<T>
{
    // just an example method showing that ThingInfo needs to know about
    // the type parameter T
    T getThing();
}

class Thing<T extends Thing<T>>
{
    // I need to be able to return a ThingInfo with the type parameter
    // of the sub class of Thing. ie. ThingA.getThingInfo() must return
    // a ThingInfo<ThingA>.
    // This is where Java would benefit from self types, as I could declare
    // the method something like: ThingInfo<THIS_TYPE> getThingInfo()
    // and Thing would not need a type parameter.
    ThingInfo<T> getThingInfo()
    {
        return something;
    }
}

// example Thing implementation
class ThingA extends Thing<ThingA>
{
}

// example Thing implementation
class ThingB extends Thing<ThingB>
{
}

Пока все в порядке. Этот код работает по мере необходимости.

Мне также нужно представить безопасное отношение типа между Things.

class ThingRelation<X extends Thing<X>, Y extends Thing<Y>>
{
    X getParent()
    {
        return something;
    }

    Y getChild()
    {
        return something;
    }
}

На самом деле это не так просто, но это демонстрирует необходимость, я думаю. Тем не менее, все это хорошо, ошибок пока нет. Теперь ThingRelationнужен метод, который принимает аргумент ThingRelationмежду Yи некоторым другим Thing. Поэтому я меняю ThingRelationна следующее:

class ThingRelation<X extends Thing<X>, Y extends Thing<Y>>
{
    X getParent()
    {
        return something;
    }

    Y getChild()
    {
        return something;
    }

    <Z extends Thing<Z>> void useRelation(ThingRelation<Y, Z> relation)
    {
        // do something;
    }
}

Но теперь я получаю эту ошибку при компиляции:

type argument Y is not within bounds of type-variable X
  where Y,X are type-variables:
    Y extends Thing<Y> declared in class ThingRelation
    X extends Thing<X> declared in class ThingRelation

Ошибка в строке, начинающейся<Z extends Thing<Z>>....

В чем может быть проблема?

Обновление:Версия javac1.7.0_05.

6
задан Bohemian 19 August 2012 в 19:00
поделиться