В Java я могу сказать class SomeClass<T extends Thing>
. Но есть ли способ сказать, что я хочу T
продлить либо Thing
, либо SomethingElse
?Есть ли способ в Java Generics сказать, что «T extends Thing или T extends SomethingElse»?
ответ
Невозможно сделать это в Java, как было предложено - Java не поддерживается algebraic data types.
ограничения Generic типа Java должны унифицировать к одному типу так же, как выражения в Java должны объединить к одному типу - например. он является недействительным по той же причине, как пытаться использовать :
{ArrayList | HashSet} collection = ..;
Однако, так как они оба этих типа унифицировать в коллекции, то справедливо следующее:
Collection collection = createArrayListOrHashSetAndReturnACollection();
Теперь, в зависимости по необходимости есть два общих способа, в которых задача может обрабатываться, возвращаясь к вышеуказанным ограничениям:
Типы, о которых идет речь, могут распространяться (или лучше наследовать) из общего типа и могут затем объединить вокруг этого типа. Это может включать модификацию рассматриваемых типов по мере необходимости.
Может быть создан другой тип (поддерживаемый интерфейсом, возможно, с использованием композиции), который действует как прокси для типов Thing/SomethingElse. Общее ограничение теперь объединяет в этом новом типе/интерфейсе.
Удалить ограничение типа и унифицировать вокруг объекта; это наименее утонченная унификация каждого не примитивного типа в Java.
Хотя это не является ограничением «ООП», дженериков/шаблонов или статических типов-систем в целом, это является как Java работает: Неа, не может сделать что.
Нет, нет. На каждом объектно-ориентированном языке класс может распространяться только на один класс.
Вместо этого, вы можете использовать что-то вроде:
MyClassOne расширяет то
MyClassTwo расширяет SomethingElse
если (...)
MyClassOne
еще
MyClassTwo
Не говорите «каждый» язык так небрежно, так как ответ «не так» * при этом. Кроме того, языки ООП * могут * поддерживать не номинативные типы. Теперь вопрос * есть * о Java и использует правильный (не «каждый») контекст * can * и должен использоваться для определения поведения в конкретном контексте. – user2864740
@ user2864740 Не будьте так жестоки с ним. Люди ошибаются. –
@AvivCohn Я не считаю это настолько суровым (после моих ревизий); и я даже не проголосовал. Скорее это объясняет одну из основных проблем с ответом, как исправить это, почему это было беспощадно проголосовано. – user2864740
You мог сделать это следующим образом
public abstract class SomeClass<T>{
}
public class StringSomeClass : SomeClass<String>{
}
public class IntegerSomeClass : SomeClass<Integer>{
}
на самом деле существует очень хорошо известное кодирование алгебраических типов данных в Java. Он называется шаблоном посетителя. И есть даже временное решение для компиляции, чтобы упростить реализацию этого шаблона: см. Проект adt4j в Github.
Но то, что вы ищете, это Generalized algebraic data type (GADT).
Оказывается, что Java также поддерживает GADT (и без литья типов). См. Этот пример как пример изящного решения проблемы выражения с помощью GADT: https://gist.github.com/jbgi/208a1733f15cdcf78eb5 - В этом коде мы определяем класс Term, где T статически ограничено как Integer, так и Boolean.
- 1. java generics T extends Simpletype?
- 2. Java generics - почему разрешено «extends T», но не «реализует T»?
- 3. В чем разница между «? Extends E» и «T extends E»?
- 4. Java Generics extends Loop
- 5. Общие сведения о Java Generics <T extends Class> и <? extends Class>
- 6. Generics Abstract Extends Error
- 7. Как отсортировать список <? extends T>
- 8. Java- Значение <T extends Comparable <T>>?
- 9. Класс <? extends T>
- 10. Java Generics - использование ключевого слова extends
- 11. Разница между генериками <T extends Number & Comparable <T>> и T extends Comparable <? extends Number>
- 12. Каково значение T, когда тип параметра метода равен <? extends T> в Java Generics?
- 13. Java generics extends in type параметр
- 14. Generics, V extends T, без ошибок, даже если несовместимые типы
- 15. Java Generics wildcard extends problem
- 16. реализует vs extends в generics в Java
- 17. Selma Mapper Generics Convert BaseMapper <T extends BaseDomain, D extends BaseDTO>
- 18. В чем смысл T extends SomeClass?
- 19. Есть ли эквивалент <? extends T>, <? super T> в C++?
- 20. Коллекция <? extends T> vs Collection <T>
- 21. Различия между `копия (список <? super T> Dest, Список <? extends T> ЦСИ)` и `копирования (Список <T> Dest, Список <? extends T> ЦСИ)`
- 22. В чем разница между <T> и <T extends Object> в java?
- 23. TypeScript: Class generics - что-то вроде класса Java <T extends Foo>
- 24. Java 1.7: Сумма Iterable <T extends Number>
- 25. В java generics какая разница между символами подстановки: <? extends Object> и <? extends T>?
- 26. Почему T extends Comparable <? super T> включает T? Значение включает Comparable <T>?
- 27. Array of <? extends T> в Java
- 28. Зачем вам нужно «? Extends» в generics
- 29. Разница между списком <T> и Список <? extends T>
- 30. Как сделать «новый» универсального класса T extends AbstractClass (JAVA)
Нет, нет. Представьте, что вы компилятор. Как бы вы набрали чек, когда вы вызываете метод, который не находится в обеих Thing и SomethingElse. Можете ли вы добавить интерфейс с помощью методов, которые вам нужны, или вы можете разлить свой метод/класс. –
Нет, нет. Дженерики должны объединяться. – user2864740
И как бы ' 'work, если я сделал' final X x = getx() 'и пытался вызвать методы на' x'? –