Je suis tombé sur un réponse qui suggère d'utiliser
var list = new ArrayList();
J'ai été surpris de trouver un type brut ici, et je me demande simplement: var
utilise-t-il <>
"Automatiquement?
(en attendant, la réponse a été modifiée pour utiliser <String>
, mais je suis toujours curieux de savoir mais des "principes" ici)
J'ai vu d'autres questions telles que this , mais elles utilisent toutes l'opérateur diamant:
var list = new ArrayList<>();
Maintenant, je me demande simplement: var
change-t-il la façon dont nous devrions (ne pas) utiliser les types bruts? Ou est-ce que cette suggestion de laisser de côté <>
Est simplement une mauvaise pratique?
Je suis tombé sur une réponse qui suggère d'utiliser ...
J'ignorerais cette réponse, car comme vous le signalez, il utilise des types bruts et il tape list
comme spécifiquement ArrayList
. (Mise à jour: le répondeur a modifié leur réponse pour ajouter un type d'élément.) À la place:
List<AppropriateElementType> list = new ArrayList<>();
Selon le deuxième réponse que vous avez liée , var
will oblige le compilateur à déduire un type d'élément du côté droit si vous incluez le <>
, En choisissant le type le plus spécifique possible. Dans var list = new ArrayList<>();
, ce serait ArrayList<Object>
, Car il n'a rien de plus spécifique à choisir.
Mais , ceci:
var list = new ArrayList();
... sans <>
, utilise un type brut (ArrayList
), pas un type paramétré avec Object
comme paramètre (ArrayList<Object>
), qui est différent.
Si l'utilisation de list
est suffisamment contenue (quelques lignes dans une méthode), le faire taper ArrayList<X>
Plutôt que List<X>
Peut être acceptable (dépend de votre style de codage), dans quel cas:
var list = new ArrayList<AppropriateElementType>();
Mais généralement, je préfère coder sur l'interface plutôt que sur la classe concrète, même avec les locaux. Cela dit, avec les sections locales, c'est c'est moins important qu'avec les membres d'instance, et var
est pratique.
Il est légal d'utiliser à la fois var
et diamond
, mais le type déduit changera:
var list = new ArrayList<>(); // DANGEROUS: infers as ArrayList<Object>
Pour son inférence, diamond
peut utiliser le type cible (généralement, le côté gauche d'une déclaration) ou les types d'arguments constructeur. Si aucun n'est présent, il revient au type applicable le plus large, qui est souvent Object
1.
Avec les méthodes diamond
et génériques, des informations de type supplémentaires peuvent être fournies par des arguments réels au constructeur ou à la méthode, ce qui permet de déduire le type voulu1:
var list = List.of(BigInteger.ZERO); // OK: infers as List<BigInteger>
var list = new ArrayList<String>( ); // OK: infers as ArrayList<String>
Compte tenu de ce qui précède, je ne recommande pas d'effectuer les opérations suivantes (car vous obtiendrez le type brut ArrayList
):
var list = new ArrayList(); // DANGEROUS: infers as ArrayList
var
.var
avec diamond
1.1 - ( Consignes de style pour l'inférence de type variable locale: G6. Soyez prudent lorsque vous utilisez var avec diamant ou des méthodes génériques.