Do final static variables operations happen in run-time or compile time ? For example:
public static final int ID_1 = 1;
public static final int ID_2 = 2;
p
There is a hint here: https://docs.oracle.com/javase/tutorial/java/javaOO/classvars.html
It says:
If a primitive type or a string is defined as a constant and the value is known at compile time, the compiler replaces the constant name everywhere in the code with its value.
So once that is done and you end up with 1 + 2
in the method, it would be logical for that to be optimized as well and just use the 3
at compile time.
To prove it in practice, you can compile your code and then decompile it to see what's going on.
I tried with JD-GUI and this is what I got when decompiling your code:
public class TestCompileOrRuntime
{
public static final int ID_1 = 1;
public static final int ID_2 = 2;
public static int test()
{
return 3;
}
}
So it looks in this case the compiler is solving the operation in compile time.
It's a compile time operation (I get a method local iconst_3
below). We can directly examine the generated bytecode with javap -v
. I created a class Main
like,
package com.stackoverflow;
public class Main {
public static final int ID_1 = 1;
public static final int ID_2 = 2;
public static int test() {
return ID_1 + ID_2; // <-- Compile time.
}
}
and then ran javap -v
to get
Classfile /home/efrisch/workspace/StackOverflow/bin/com/stackoverflow/Main.class
Last modified Aug 22, 2015; size 410 bytes
MD5 checksum 6ba30603e8f16cbebc681a84061d38c3
Compiled from "Main.java"
public class com.stackoverflow.Main
minor version: 0
major version: 52
flags: ACC_PUBLIC, ACC_SUPER
Constant pool:
#1 = Class #2 // com/stackoverflow/Main
#2 = Utf8 com/stackoverflow/Main
#3 = Class #4 // java/lang/Object
#4 = Utf8 java/lang/Object
#5 = Utf8 ID_1
#6 = Utf8 I
#7 = Utf8 ConstantValue
#8 = Integer 1
#9 = Utf8 ID_2
#10 = Integer 2
#11 = Utf8 <init>
#12 = Utf8 ()V
#13 = Utf8 Code
#14 = Methodref #3.#15 // java/lang/Object."<init>":()V
#15 = NameAndType #11:#12 // "<init>":()V
#16 = Utf8 LineNumberTable
#17 = Utf8 LocalVariableTable
#18 = Utf8 this
#19 = Utf8 Lcom/stackoverflow/Main;
#20 = Utf8 test
#21 = Utf8 ()I
#22 = Utf8 SourceFile
#23 = Utf8 Main.java
{
public static final int ID_1;
descriptor: I
flags: ACC_PUBLIC, ACC_STATIC, ACC_FINAL
ConstantValue: int 1
public static final int ID_2;
descriptor: I
flags: ACC_PUBLIC, ACC_STATIC, ACC_FINAL
ConstantValue: int 2
public com.stackoverflow.Main();
descriptor: ()V
flags: ACC_PUBLIC
Code:
stack=1, locals=1, args_size=1
0: aload_0
1: invokespecial #14 // Method java/lang/Object."<init>":()V
4: return
LineNumberTable:
line 4: 0
LocalVariableTable:
Start Length Slot Name Signature
0 5 0 this Lcom/stackoverflow/Main;
public static int test();
descriptor: ()I
flags: ACC_PUBLIC, ACC_STATIC
Code:
stack=1, locals=0, args_size=0
0: iconst_3
1: ireturn
LineNumberTable:
line 9: 0
LocalVariableTable:
Start Length Slot Name Signature
}
SourceFile: "Main.java"