Question

Lorsque le compilateur Java sélectionne automatiquement une primitive dans la classe wrapper, quel code est-il généré en arrière-plan? J'imagine qu'il appelle:

  • La méthode valueOf () sur le wrapper
  • Le constructeur du wrapper
  • Une autre magie?
Était-ce utile?

La solution

Vous pouvez utiliser l'outil javap pour voir par vous-même. Compilez le code suivant:

public class AutoboxingTest
{
    public static void main(String []args)
    {
        Integer a = 3;
        int b = a;
    }
}

Pour compiler et désassembler:

javac AutoboxingTest.java
javap -c AutoboxingTest

Le résultat est:

Compiled from "AutoboxingTest.java"
public class AutoboxingTest extends java.lang.Object{
public AutoboxingTest();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."<init>":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   iconst_3
   1:   invokestatic    #2; //Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
   4:   astore_1
   5:   aload_1
   6:   invokevirtual   #3; //Method java/lang/Integer.intValue:()I
   9:   istore_2
   10:  return

}

Ainsi, comme vous pouvez le constater, la sélection automatique appelle la méthode statique Integer.valueOf () , et la boîte automatique appelle intValue () sur le Integer objet. Il n'y a rien d'autre, vraiment - c'est juste du sucre syntaxique.

Autres conseils

J'ai proposé un test unitaire qui prouve qu'Integer.valueOf () est appelé à la place du constructeur du wrapper.

import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertSame;

import org.junit.Test;

public class Boxing {
    @Test
    public void boxing() {
        assertSame(5, 5);
        assertNotSame(1000, 1000);
    }
}

Si vous consultez la documentation de l'API pour Integer # valueOf (int) , vous verrez qu'il a été ajouté dans JDK 1.5. Tous les types d'encapsuleurs (qui n'en possédaient pas déjà) avaient des méthodes similaires ajoutées pour prendre en charge l'autoboxing. Pour certains types, il existe une exigence supplémentaire, décrite dans le JLS:

  

Si la valeur p à encadrer est vrai , faux , un octet , un dans la plage \ u0000 à \ u007f , ou un int ou numéro court compris entre -128 et 127 , puis laissez r1 et r2 le résultat de deux conversions de p . Il est toujours vrai que r1 == r2 . & # 167; 5.1.7

Il est intéressant de noter que les longs ne sont pas soumis à la même exigence, bien que les valeurs Long de la plage -128..127 soient mises en cache dans l'implémentation de Sun. tout comme les autres types intégraux.

Je viens également de découvrir que, dans ma copie de Le langage de programmation Java indique les valeurs char de \ u0000 à \ u00ff , mais bien entendu, la limite supérieure la spécification est \ u007f (et le JDK de Sun est conforme à la spécification dans ce cas).

Je vous conseillerais quelque chose comme jad et de décompiler beaucoup de code. Vous pouvez en apprendre un peu plus sur ce que fait réellement Java.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top