Расширение общего абстрактного класса и правильное использование Super

public abstract class AbstractTool<AT extends AbstractThing> {
    protected ArrayList<AT> ledger;
    public AbstractTool() {
        ledger = new ArrayList<AT>();
    }

    public AT getToolAt(int i) {
        return ledger.get(i);
    }

    // More code Which operates on Ledger ...

}

public class Tool<AT extends AbstractThing> extends AbstractTool {
    public Tool() {
        super();
    }
}

Как правильно вызвать super для передачи AT generic Tool в конструктор AbstractTool?

Кажется, что я выбираю AT, когда объявляю Tool (Скажем, Tool<Thing>), что я всегда возвращаю AbstractThing вместо Thing. Это, похоже, превзошло цель дженериков...

Справка

Ответ 1

public class Tool<AT extends AbstractThing> extends AbstractTool<AT> {

Другими словами, если вы расширяете или реализуете что-то с помощью generics, не забудьте указать для них аргументы generics.

Ответ 2

Разве это не должно быть Tool<AT extends...> extends AbstractTool<AT>?

Ответ 3

Я думаю, что вы, вероятно, захотите:

   public abstract class AbstractTool<AT extends AbstractThing> {
        protected List<AT> ledger = new ArrayList<AT>();

        public AT getToolAt(int i) {
            return ledger.get(i);
        }

        // More code Which operates on Ledger ...

    }

    public class Tool extends AbstractTool<Thing> {
        // Tool stuff ...
    }

Так как Tool - это конкретный класс, он не нуждается в параметризации. Нет необходимости в конструкторах, если вы инициализируете List (oh и помните, чтобы программировать интерфейс) в объявлении, и поскольку он защищен, подклассы могут получить к нему доступ напрямую.