Cela dépend de ce que vous devez faire. Vous devez utiliser le délimitée type de paramètre que si vous vouliez faire quelque chose comme ceci:
public <T extends Shape> void addIfPretty(List<T> shapes, T shape) {
if (shape.isPretty()) {
shapes.add(shape);
}
}
Ici, nous avons un List<T> shapes
et T shape
, donc nous pouvons en toute sécurité shapes.add(shape)
. Si elle a été déclarée List<? extends Shape>
, vous pouvez ne PAS en toute sécurité add
pour elle (parce que vous pouvez avoir un List<Square>
et Circle
).
Donc, en donnant un nom à un délimitée paramètre de type, nous avons la possibilité de les utiliser ailleurs dans notre méthode générique. Cette information n'est pas toujours nécessaire, bien sûr, donc si vous n'avez pas besoin d'en savoir beaucoup sur le type (par exemple, votre drawAll
), puis il suffit de joker, c'est suffisant.
Même si vous n'êtes pas en se référant à la délimitée paramètre de type nouveau, un délimitée paramètre de type est toujours nécessaire si vous disposez de plusieurs limites. Voici une citation de Angelika Langer Java Génériques Faq
Quelle est la différence entre un générique lié et un paramètre de type lié?
Un joker peut avoir qu'une seule tenue, alors qu'un paramètre de type peut avoir plusieurs limites.
Un joker peut avoir une baisse de régime ou une limite supérieure, alors qu'il n'y a pas une telle chose comme une limite inférieure pour un paramètre de type.
Générique de limites et d'un paramètre de type de limites sont souvent confondus, car ils sont tous deux appelés limites et ont en partie similaire à la syntaxe. [...]
Syntaxe:
type parameter bound T extends Class & Interface1 & … & InterfaceN
wildcard bound
upper bound ? extends SuperType
lower bound ? super SubType
Un joker peut avoir qu'un seul tenu, soit une baisse ou une limite supérieure. Une liste des génériques de limites n'est pas autorisée.
Un paramètre de type, en contraste, peut avoir plusieurs limites, mais il n'y a pas une telle chose comme une limite inférieure pour un paramètre de type.
Citations de Efficace Java 2nd Edition, Point 28: Utilisation délimitée des caractères génériques pour augmenter l'API de flexibilité:
Pour une flexibilité maximale, utilisez les caractères génériques types des paramètres d'entrée qui représentent les producteurs ou les consommateurs. [...] PECS stands pour le producteur-extends
, de la consommation-super
[...]
Ne pas utiliser de caractères génériques types de types de retour. Plutôt que de fournir une plus grande flexibilité pour vos utilisateurs, il serait forcer à utiliser des types génériques dans le code client. Correctement utilisés, les types génériques sont presque invisible pour les utilisateurs d'une classe. Ils provoquent des méthodes pour accepter les paramètres qu'ils doivent accepter et de rejeter ceux qu'ils devraient rejeter. Si l'utilisateur de la classe a à réfléchir sur les types génériques, il y a probablement quelque chose de mal avec la classe de l'API.
En appliquant les PECS principe, nous pouvons maintenant revenir à notre addIfPretty
exemple et de le rendre plus souple par écrit les éléments suivants:
public <T extends Shape> void addIfPretty(List<? super T> list, T shape) { … }
Maintenant, nous pouvons addIfPretty
, disons, un Circle
, pour un List<Object>
. C'est évidemment typesafe, et pourtant notre déclaration d'origine n'était pas assez souple.
Questions connexes
Résumé
- N'utilisez délimitée paramètres de type et les jokers, ils augmentent la flexibilité de votre API
- Si le type nécessite plusieurs paramètres, vous n'avez pas d'autre choix que d'utiliser délimitée paramètre de type
- si le type nécessite une limite inférieure, vous n'avez pas d'autre choix que d'utiliser délimitée générique
- "Producteurs" ont upperbounds, "consommateurs" qui ont lowerbounds
- Ne pas utiliser de caractères génériques dans les types de retour