简体   繁体   中英

Java difference between static and final static variable initialization

public class StaticTest {

    private static StaticTest stObj=new StaticTest();
    private static int VAR1=10;
    private static final int VAR2=20;

    public StaticTest() {

        System.out.println("Var1 : "+VAR1);
        System.out.println("Var2 : "+VAR2);
    }

    public static void main(String[] args) {
        System.out.println("VAR1 after constrution : "+StaticTest.VAR1);
    }

}

Output :

Var1 : 0 Var2 : 20 VAR1 after constrution : 10

Why is this different behavior for VAR1 and VAR2 ?

The static fields get initialized one by one in order of declaration. In your particular case you initialize StaticTest stObj first. This gets executed before the initialization of the VAR1 . Thus VAR1 bears its default value when printing.

However VAR2 is compile-time constant, thus the compiler optimizes its initialization and it is initialized first. That way one of the variables is initialized by the time you call the constructor, the other -not.

VAR2 is a compile-time constant, so its value is "baked in" to every call site. It therefore doesn't matter that you use it before you would expect to see it initialized. If you change it to something which isn't a constant as far as the compiler is concerned, eg

private static final int VAR2 = "xyz".length();

then you'll see the same behaviour as for VAR1 (in terms of the output).

See section 15.28 of the JLS for more information about constant expressions.

VAR1 can be changed, VAR2 can't.

Try this:

private static int VAR1=10;
private static final int VAR2=20;

public static void main(String[] args) {
    VAR1 = 25;
    VAR2 = 35; // You'll find a compilation error here.
}

VAR2 cannot be changed one the class has been initialised, whereas any instance of the class can change VAR later on.

The issue here is that you're referring to the variable before it has been fully initialised.

private static StaticTest stObj=new StaticTest();
private static int VAR1=10;
private static final int VAR2=20;

You're creating an instance of the class when loading the class itself, before the other static members have been initialised.

Check the Java Language Specifications for more details (Chapter 12) .

(Generally, creating an instance of the class during its own construction will lead to problems: you should avoid this.)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM