Question Quand utiliser les types primitif et quand référence en Java


Dans quel cas devriez-vous utiliser des types primitifs (int) ou des types de référence (Integer)?

Ce question a suscité ma curiosité.


20
2018-03-24 15:38


origine


Réponses:


Dans quel cas devriez-vous utiliser primitif   les types(int) ou types de référence   (Integer)?

En règle générale, je vais utiliser une primitive (telle que int) sauf si je dois utiliser une classe qui enveloppe une primitive.

L'un des cas où il faut utiliser une classe de wrapper telle que Integer est dans le cas de l'utilisation génériques, comme Java ne supporte pas l'utilisation de types primitifs comme paramètres de type:

List<int> intList = new ArrayList<int>();               // Not allowed.
List<Integer> integerList = new ArrayList<Integer>();   // Allowed.

Et, dans de nombreux cas, je profiterai de mise en boîte automatique et déballage, je n'ai donc pas à effectuer de conversions explicites de primitives vers sa classe wrapper et inversement:

// Autoboxing will turn "1", "2", "3" into Integers from ints.
List<Integer> numbers = Arrays.asList(1, 2, 3); 

int sum = 0;

// Integers from the "numbers" List is unboxed into ints.
for (int number : numbers) {
  sum += number;
}

De plus, en tant que remarque supplémentaire, lors de la conversion de primitives en objets de classe wrapper, et lorsque des instances uniques d’objets ne sont pas nécessaires, utilisez la commande valueOf méthode fournie par la méthode wrapper, car elle effectue la mise en cache et renvoie la même instance pour une certaine valeur, réduisant ainsi le nombre d'objets créés:

Integer i1 = Integer.valueOf(1);   // Prefer this.
Integer i2 = new Integer(1);       // Avoid if not necessary.

Pour plus d'informations sur le valueOf méthodes, la spécification API pour le Integer.valueOf La méthode peut servir de référence pour savoir comment ces méthodes se comporteront dans les classes wrapper des primitives.


22
2018-03-24 16:32



Cela dépend vraiment du contexte. Préférez d'abord le primitif, car il est plus intuitif et a moins de surcharge. Si ce n'est pas possible pour des raisons génériques / autoboxing, ou si vous voulez qu'elle soit annulable, optez pour le type de wrapper (type complexe comme vous l'appelez).


9
2018-03-24 15:40



Les règles générales à suivre lors de la création d'une API peuvent être résumées comme suit:

  1. Si la méthode doit retourner une valeur, utiliser un type primitif
  2. Si la méthode ne s'applique pas toujours (par exemple: getRadioId (...) sur un objet où cet identifiant n'existe pas), renvoyez un entier et spécifiez dans les JavaDocs que la méthode renverra nullement dans certains cas.

Sur # 2, recherchez les NPE lors de la sélection automatique. Si vous avez une méthode définie comme:

public Integer getValue();

Et puis appelez comme suit:

int myValue = getValue();

Dans le cas où getValue () renvoie null, vous obtenez un NPE sans cause évidente.


3
2018-03-24 16:19



Ma règle de base est la suivante: utiliser des primitives encadrées uniquement lorsqu'il est nécessaire de compiler le code. Les seuls endroits de votre code contenant les noms des classes d’encapsulation primitives sont les paramètres de type générique et les appels de méthode statiques:

List<Integer> intList = new ArrayList<Integer>();

int n = Integer.parseInt("123");

C'est le conseil que je donnerais aux nouveaux programmeurs Java. Au fur et à mesure qu’ils en apprendront davantage, ils se heurteront à des situations où ils devront faire preuve de plus de discernement, comme dans le cas des cartes ou des bases de données, mais ils devraient également mieux comprendre la différence entre les primitives

L'autoboxing nous tente de croire int et Integer (par exemple) sont interchangeables, mais c'est un piège. Si vous mélangez les deux types de valeur sans distinction, vous pouvez finir par comparer deux valeurs Integer avec ==ou en essayant de déballer un null sans le savoir. Les bugs qui en résultent peuvent être intermittents et difficiles à localiser.

Cela n’aide pas à comparer des primitives en boîte avec ==  parfois fonctionne comme s'il faisait une comparaison de valeur. C'est une illusion causée par le fait que les valeurs dans une certaine plage sont automatiquement mises en cache lors du processus de sélection automatique. C'est le même problème que nous avons toujours eu avec les valeurs de String: en les comparant avec == parfois "fonctionne" parce que vous comparez en fait deux références au même objet mis en cache.

En ce qui concerne les chaînes, nous pouvons simplement dire aux n00bs de ne jamais les comparer avec ==, comme nous le faisons depuis le début. Mais en comparant les primitifs avec == est parfaitement valide L'astuce (grâce à l'autoboxing) est de s'assurer que les valeurs sont vraiment des primitives. Le compilateur va maintenant nous laisser déclarer une variable comme Integer et l'utiliser comme si c'était un int; cela signifie que nous devons exercer un plus grand degré de discipline et le traiter comme une erreur lorsque quelqu'un le fait sans raison valable.


3
2018-03-24 17:20



Depuis que Java fait quelque chose appelé boxe automatique et auto-unboxing, vous devriez utiliser le type primitif int dans la plupart des cas à cause de moins de frais généraux.

La seule fois où vous devez absolument utiliser Integer est en génériques.

List<int> list; // won't compile
List<Integer> list; // correct

2
2018-03-24 15:41



Plutôt que de les appeler "types complexes", il serait préférable de considérer Integer, Double, etc. comme "Classes", et int, double, etc. comme "primitives".

Si vous faites des calculs sophistiqués, la représentation numérique basée sur les classes comme Integer et Double sera lourde et ralentira - de nombreuses opérations mathématiques ne peuvent être effectuées qu'avec des primitives.

D'un autre côté, si vous essayez de placer vos numéros dans des collections telles que Listes et Cartes, ces collections ne peuvent contenir que des objets - et vous devez donc utiliser (ou convertir) des classes comme Integer et Double.

Personnellement, j'utilise des primitives chaque fois que je peux m'en sortir et je ne les convertis que dans les représentations de classe comme Integer lorsqu'il est temps de faire des entrées ou des sorties, et le transport nécessite ces représentations.

Toutefois, si vous ne faites pas de calcul du tout, et que vous transmettez simplement les valeurs directement dans votre code, vous pourriez vous éviter des problèmes en traitant exclusivement les formulaires basés sur les classes (comme Integer).


1
2018-03-24 15:46



Je ne pense pas qu'il y ait une règle en tant que telle. Je choisirais les types plutôt que les primitives (Integer over int) lorsque j'écrirai des signatures de méthode, des cartes, des collections, des objets de données qui circulent. En tant que tel, je voudrais quand même utiliser Integer au lieu de int même à l'intérieur des méthodes, etc. Mais si vous pensez que c'est trop de problème (pour taper un "eger" supplémentaire), alors vous pouvez utiliser ints pour les variables locales.


0
2018-03-24 15:41



Si vous voulez définirAttribute en session, vous devez utiliser Object comme Integer, Boolean, String dans les servlets. Si vous souhaitez utiliser une valeur, vous pouvez utiliser des types primitifs. Les objets peuvent être nuls mais pas les primitives. Et si vous voulez comparer les types de primitives, utilisez == mais les objets utilisent .equals car dans la comparaison d'objets ==, les valeurs ne sont pas identiques à celles des objets. Et l'utilisation de primitives accélère le code.


0
2018-03-24 15:54