Chargement de classe vs initialisation: variable finale statique Java [dupliquer]

Aug 22 2020

Example.java

public class Example {

    static final int i = 10;
    static int j = 20;
    static {
        System.out.println("Example class loaded and initialized");
    }
}

Use.java

import java.util.Scanner;
public class Use {
    public static void main(String args[]){
        Scanner sc = new Scanner(System.in);
        int ch = 1;
        while(ch != 0) {
            System.out.print("Enter choice: ");
            ch = sc.nextInt();

            if (ch == 1) {
                System.out.println("Example's i = " + Example.i);
            } else if(ch == 2){
                System.out.println("Example's j = " + Example.j);
            }
        }
    }
}

Quand je cours avec java -verbose:class Use, et donne l'entrée comme 1alors la sortie est 10c'est-à - dire la ivaleur constante . Mais la Exampleclasse n'est pas encore chargée. Cependant, lorsque je donne une entrée comme 2, alors seulement la Example classe est chargée dans la JVM, comme visible par la sortie verbeuse , puis le bloc statique à l 'intérieur de l' exemple est exécuté et jla valeur de l 'est également initialisée puis imprimée.

Ma requête est la suivante: si pour l'entrée, 1c'est-à-dire lorsque la valeur finale statique (constante) d'une classe Exampleest demandée dans une autre classe Use, d'où cette valeur constante est-elle récupérée si la classe Examplen'a jamais été chargée dans la JVM jusque-là? Quand et comment le final statique a-t-il été iinitialisé et stocké dans la mémoire JVM?

Réponses

2 Joni Aug 22 2020 at 17:31

Selon la section 12.4.1 de la spécification du langage Java (emphase ajoutée):

Une classe ou un type d'interface T sera initialisé immédiatement avant la première occurrence de l'un des éléments suivants:

  • T est une classe et une instance de T est créée.

  • Une méthode statique déclarée par T est invoquée.

  • Un champ statique déclaré par T est attribué.

  • Un champ statique déclaré par T est utilisé et le champ n'est pas une variable constante (§4.12.4).

Une variable constante est une variable finale qui est initialisée avec une expression constante . Dans votre code, Example.iest une variable constante et ne provoque donc pas le chargement de la classe.

Donc, si la classe n'est pas chargée, d'où vient la valeur com?

La spécification du langage nécessite que le compilateur intègre sa valeur. De la section de compatibilité binaire 13.1 :

  1. Une référence à un champ qui est une variable constante (§4.12.4) doit être résolue au moment de la compilation en la valeur V indiquée par l'initialiseur de la variable constante.

    Si un tel champ est statique, aucune référence au champ ne doit être présente dans le code d'un fichier binaire, y compris la classe ou l'interface qui a déclaré le champ. Un tel champ doit toujours apparaître comme initialisé (§12.4.2); la valeur initiale par défaut du champ (si différente de V) ne doit jamais être observée.