Java中無論創建多少對象,靜態數據都只占一份存儲區域。
下面程序示例靜態存儲區域的初始化:
//: initialization/StaticInitialization.java // Specifying initial values in a class definition. class Bowl{ // 構造器 Bowl(int marker){ System.out.println("Bowl("+marker+")"); } // 方法 void f1(int marker){ System.out.println("f1("+marker+")"); } } class Table{ // 靜態域 static Bowl bowl1 = new Bowl(1); // 構造器 Table(){ System.out.println("Table()"); bowl2.f1(1); } // 方法 void f2(int marker){ System.out.println("f2("+marker+")"); } // 靜態域 static Bowl bowl2 = new Bowl(2); } class Cupboard{ // 非靜態域 Bowl bowl3 = new Bowl(3); // 靜態域 static Bowl bowl4 = new Bowl(4); // 構造器 Cupboard(){ System.out.println("Cupboard()"); bowl4.f1(2); } // 方法 void f3(int marker){ System.out.println("f3("+marker+")"); } // 構造器 static Bowl bowl5 = new Bowl(5); } public class StaticInitialization{ public static void main(String[] args){ System.out.println("Creating new Cupboard() in main"); new Cupboard(); System.out.println("Creating new Cupboard() in main"); new Cupboard(); table.f2(1); cupboard.f3(1); } static Table table = new Table(); static Cupboard cupboard = new Cupboard(); }
---------- Java ---------- Bowl(1) Bowl(2) Table() f1(1) Bowl(4) Bowl(5) Bowl(3) Cupboard() f1(2) Creating new Cupboard() in main Bowl(3) Cupboard() f1(2) Creating new Cupboard() in main Bowl(3) Cupboard() f1(2) f2(1) f3(1) Output completed (0 sec consumed) - Normal Termination
初始化的順序是:先靜態對象,而后是“非靜態”對象。
要執行main(),必須加載StaticInitialization類,然后其靜態域table和cupboard被初始化,這導致他們對應的類也被加載,並且由於它們都包含靜態的Bowl對象,因此Bowl隨后也被加載。這樣,在這個特殊的程序中的所有的類在main()開始之前就都被加載了。
個人理解: 首先從main()函數開始,加載StaticInitializaition類,然后對StaticInitializaition類中的靜態域Table進行初始化,加載Table類,Table類中包含靜態的Bowl對象,接着加載Bowl類,加載Bowl類構造器創建bowl1對象,輸出Bowl(1),加載Bowl類構造器創建bowl2對象,輸出Bowl(2);同里創建cupboard對象。
需要注意的是,bowl3是非靜態域,每次創建Cupboard對象都會創建一個Bowl對象。