84 votes

Pourquoi des valeurs de mise en cache de la classe Integer comprises entre -128 et 127?

Sujet de ma Question précédente, la Confusion dans la méthode Integer.valueOf(String) , nous savons qu' Integer class a un cache qui stocke les valeurs entre -128 et 127.

Je me demandais, pourquoi entre -128 et 127?

Entier.valueOf() documentation a déclaré qu'il "cache fréquemment demandé des valeurs" . Mais n'valeurs entre -128 et 127 sont demandés pour de vrai? J'ai pensé souvent demandé valeurs sont très subjectives.
Est-il possible que la raison derrière tout cela?

À partir de la documentation a également déclaré: "..et peut mettre en cache d'autres valeurs en dehors de cette plage."
Comment cela peut être réalisé?

112voto

assylias Points 102015

Je me demandais, pourquoi entre -128 et 127?

Une large gamme de nombres entiers peuvent être mis en cache, mais au moins, ceux compris entre -128 et 127 doit être mis en cache, car il est mandaté par le Langage Java Specification (l'emphase est mienne):

Si la valeur de p étant le coffret est vrai, de faux, d'un octet, ou un char dans la gamme \u0000 à \u007f, ou un int ou un numéro court entre -128 et 127 (inclus), puis laissez r1 et r2 les résultats de deux de boxe conversions de p. C'est toujours le cas que r1 == r2.

La justification de cette exigence est expliqué dans le même paragraphe:

Idéalement, la boxe une valeur primitive p, serait toujours un rendement identique de référence. Dans la pratique, cela peut ne pas être réalisable en utilisant les techniques de mise en œuvre. Les règles ci-dessus sont un compromis pragmatique. La finale de la clause ci-dessus exige que certaines valeurs communes, toujours encadré dans impossibles à distinguer les objets. [...]

Cela garantit que, dans la plupart des cas, le comportement sera le désirer, sans imposer indûment les performances, en particulier sur les petits appareils. Moins de mémoire limitée implémentations pourrait, par exemple, la mise en cache de tous les char et short de valeurs, ainsi que int et long valeurs dans la plage de -32K à +32K.


Comment puis-je mettre en cache d'autres valeurs en dehors de cette plage.?

Vous pouvez utiliser l' -XX:AutoBoxCacheMax de la JVM de l'option, qui n'est pas vraiment documenté dans la liste des accès disponibles Options JVM. Toutefois, il est mentionné dans les commentaires à l'intérieur de l' Integer classe autour de la ligne 590:

La taille du cache peut être contrôlé par l' -XX:AutoBoxCacheMax=<size> option.

Notez que cette mise en œuvre est spécifique et peuvent ou peuvent ne pas être disponibles sur d'autres machines virtuelles.

23voto

Evgeniy Dorofeev Points 52031

-128 à 127 est la taille par défaut. Mais javadoc indique également que la taille du cache Integer peut être contrôlée par l’option -XX:AutoBoxCacheMax=<size> . Notez qu'il ne définit que la valeur haute, la valeur basse est toujours -128. Cette fonctionnalité a été introduite dans 1.6.

En ce qui concerne pourquoi -128 à 127 - il s’agit d’une plage de valeurs en octets et il est naturel de l’utiliser pour un très petit cache.

6voto

keshlam Points 5979

La raison de la mise en cache des petits entiers, si c'est ce que vous demandez, c'est que de nombreux algorithmes utilisent de petits entiers dans leurs calculs, afin d'éviter la création de l'objet de surcharge pour ces valeurs tend à être la peine.

La question est alors de quel entier de cache. Encore une fois, en général, la fréquence à laquelle les valeurs des constantes sont utilisées tend à diminuer à mesure que la valeur absolue de la constante augmente -- tout le monde y passe beaucoup de temps en utilisant les valeurs 1 ou 2 ou 10, relativement peu de peu de gens utilisent la valeur 109 de manière très intense, moins de devra performances dépendent de la rapidité avec laquelle on peut obtenir un nombre Entier de 722.. Java a choisi d'allouer 256 emplacements couvrant la gamme d'un octet signé valeur. Cette décision peut avoir été informé par l'analyse des programmes en vigueur à l'époque, mais il est tout aussi susceptibles d'avoir été purement arbitraire. C'est un montant raisonnable de l'espace à investir, il peut être accessible rapidement (masque pour savoir si la valeur est dans le cache de la plage, puis un rapide tableau de la recherche pour accéder à la cache), et il va certainement couvrir les cas les plus courants.

En d'autres termes, je pense que la réponse à votre question est "ce n'est pas que subjectif comme vous le pensiez, mais l'exacte des limites sont en grande partie une règle-de-pouce décision ... et experiemental preuve n'a été qu'il était assez bon."

3voto

theexamtime Points 39

La valeur entière maximale pouvant être mise en cache peut être configurée via la propriété système, à savoir java.lang.Integer.IntegerCache.high ( -XX:AutoBoxCacheMax ). Le cache est implémenté à l'aide d'un tableau.

     private static class IntegerCache {
    static final int high;
    static final Integer cache[];

    static {
        final int low = -128;

        // high value may be configured by property
        int h = 127;
        if (integerCacheHighPropValue != null) {
            // Use Long.decode here to avoid invoking methods that
            // require Integer's autoboxing cache to be initialized
            int i = Long.decode(integerCacheHighPropValue).intValue();
            i = Math.max(i, 127);
            // Maximum array size is Integer.MAX_VALUE
            h = Math.min(i, Integer.MAX_VALUE - -low);
        }
        high = h;

        cache = new Integer[(high - low) + 1];
        int j = low;
        for(int k = 0; k < cache.length; k++)
            cache[k] = new Integer(j++);
    }

    private IntegerCache() {}
}
 

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X