最近在阅读孙卫琴的java面向对象一书中,看到对java中类的初始化和加载中的论述比较系统,故笔记之

1)类的初始化,JAVA在初始化一个类时,以下步骤
      A 假如类存在直接的父类,并且这个父类还没有初始化,则先初始化直接的父类
      B  假如类存在初始化的语句,那么直接执行这些初始化语句

   比如
   package init;
class Base{
static int a=1;
  static{
    System.out.println("init Base");
  }
}

class Sub extends Base{
  static int b=1;
  static{
    System.out.println("init Sub");
  }
}

public class InitTester{
  static{System.out.println("init InitTester");}

/*
  public static void main(String args[]){
    System.out.println("b="+Sub.b);  //执行这行代码时,先依次初始化Base类和Sub类
  }
*/

输出:
 init InitTester
init Base
init Sub
b=1

假如换成下面这样
 public static void main(String args[]){
    Base base;  //不会初始化Base类
    System.out.println("After defining base");
    base=new Base();  //执行这行代码时,初始化Base类
    System.out.println("After creating an object of Base");
    System.out.println("a="+base.a);
    System.out.println("b="+Sub.b);  //执行这行代码时,仅仅初始化Sub类
  }

}

  输出
 init InitTester
After defining base
init  Base
After creating an object of Base
a=1
init Sub
b=1

2) 类的初始化时机
     A 对于final类型的,如果在编译时就能计算出变量的值,则不会导致类的初始化,如下
   class Tester {
  public static final int a=2*3;
 static  {
System.out.println("hello");   ..............
}
}

public class Sample
{
  public static void main(String args[])
{  System.out.println("a="+Tester.a);
}
}

2)  package initbase;

class Base{
  static int a=1;
  static{
    System.out.println("init Base");
  }
  static void method(){
    System.out.println("method of Base");
  }
}
class Sub extends Base{
  static{
    System.out.println("init Sub");
  }
}
public class Sample{
  public static void main(String args[]){
    System.out.println("a="+Sub.a);  //仅仅初始化Base类
    Sub.method(); 
  }
}
由于静态变量a和静态方法method()在 base父类中定义,所以仅初始化Base类,没初始化SUB类
打印结果为
init Base
a=1
method of Base
这样的话,如果在调用Tester.a时,不会输出hello,