在这里首先明确,静态static关键字和jvm虚拟机常量池是两个概念。java
只是static关键字修饰常量或者变量,会在类实例化以前就放在常量池中而已。dom
static关键字jvm
由static修饰的变量,常量和方法被称为静态变量,常量和方法。测试
final关键字优化
由final修改的为常量。由final和static共同修饰的为静态常量spa
以下:测试java中静态常量和静态变量区别的样例,代表二者加载时的区别。code
StaticClass类中定义了静态常量FIANL_VALUE和静态变量VALUE,静态代码块的打印语句表示类被加载:blog
public class StaticClass { static { System.out.println("StaticClass loading..."); } public static String VALUE = "static value loading"; public static final String FIANL_VALUE = "fianl value loading"; public static final int FINAL_VALUE_INT = new Random(66).nextInt(); }
StaticClassLoadTest类用于测试静态变量的加载:内存
public class StaticClassLoadTest { public static void main(String[] args) { System.out.println("StaticClassLoadTest..."); printStaticVar(); } private static void printStaticVar() { // System.out.println(StaticClass.FINAL_VALUE_INT);//这个由于是随机数,须要出发类加载 System.out.println(StaticClass.FIANL_VALUE); //这个由于是一个常量,不须要类加载就能获得 System.out.println(StaticClass.VALUE); } }
输出:虚拟机
输出显示在打印静态常量时,StaticVar类并无被加载,在输出静态变量的前才打印类加载信息。这代表类的未加载的状况下也能引用其静态常量信息,缘由是由于常量值存储在JVM内存中的常量区中,在类不加载时便可访问。
注:通过编译优化,静态常量 FIANL_VALUE 已经存到NotInit类自身常量池中,不会加载StaticClass
可是不能说全部的静态经常使用访问都不须要类的加载,这里还要判断这个常量是否属于“编译期常量”,即在编译期便可肯定常量值。若是常量值必须在运行时才能肯定,如常量值是一个随机值,也会引发类的加载,以下:
public static final int FINAL_VALUE_INT = new Random(66).nextInt();