Карта / Generics (дженерики) / Ограничения (extends, super)

Ограничения (extends, super)

По умолчанию параметр дженерика <T> — это «любой тип». Ограничения (bounds) сужают это: можно потребовать, чтобы T обязательно был определённым типом или его наследником.

class Box<T extends Number> {   // только Number и наследники (Integer, Double...)
    T value;
}

Box<Integer> b1 = new Box<>();   // ок — Integer наследник Number
Box<String> b2 = new Box<>();    // ошибка компиляции — String не Number

Зачем это нужно: если внутри класса/метода требуется вызывать методы конкретного типа (например, doubleValue() у Number), без ограничения компилятор о них не знает — T мог бы быть чем угодно.

Копнуть глубже

Несколько ограничений сразу — через &:

<T extends Number & Comparable<T>> T max(T a, T b) {
    return a.compareTo(b) > 0 ? a : b;
}

Тут T должен быть и наследником Number, и уметь сравниваться (Comparable).

🎤 Закрыл тему, если можешь объяснить:
• зачем нужны ограничения (bounds) и как их написать (`extends`);
• как задать сразу несколько ограничений.