你們都知道,咱們能夠基於一個類建立多個該類的對象,每一個對象都擁有本身的成員,互相獨立。然而在某些時候,咱們更但願該類全部的對象共享同一個成員。此時就是 static 大顯身手的時候了!!spa
Java 中被 static 修飾的成員稱爲靜態成員或類成員。它屬於整個類全部,而不是某個對象全部,即被類的全部對象所共享。靜態成員可使用類名直接訪問,也可使用對象名進行訪問。固然,鑑於他做用的特殊性更推薦用類名訪問~~code
使用 static 能夠修飾變量、方法和代碼塊。對象
本小節,咱們先認識一下靜態變量。blog
咱們先來看一段簡單的代碼你就會明白什麼是靜態變量!內存
1 public class HelloWorld{ 2 static String name = "Hello Java";//用static修飾的變量就是靜態變量 3 public static void main(){ 4 System.out.println("經過類名訪問它:"+HelloWorld.name); 5 HelloWorld hello = new HelloWorld(); 6 System.out.println("經過對象訪問它:"+hello.name); 7 hello.name = "我是最棒的!";//使用對象名的形式來修改靜態變量的值! 8 System.out.println("經過類名訪問它:"+HelloWorld.name); 9 } 10 }
要注意哦:靜態成員屬於整個類,當系統第一次使用該類時,就會爲其分配內存空間直到該類被卸載纔會進行資源回收!~~資源
與靜態變量同樣,咱們也可使用 static 修飾方法,稱爲靜態方法或類方法。其實以前咱們一直寫的 main 方法就是靜態方法。class
靜態方法的使用以下:變量
1 public class HelloWorld{ 2 public static void print(){ 3 System.out.println("我愛Java」); 4 } 5 public static void main(String [] args){ 6 //直接實用類名調用 7 HelloWorld.print(); 8 //也能夠建立對象調用它 9 HelloWorld demo = new HelloWorld(); 10 demo.print(); 11 } 12 }
1.靜態方法中能夠直接條用同類中的靜態成員;可是不能調用非靜態成員;程序
1 public class HelloWorld{ 2 static String name = "hello"; 3 String hobby = "hello"; 4 public static void main(String [] args){ 5 System.out.println("同類中能夠直接調用靜態成員"+name); 6 System.out.println("不能夠直接調用非靜態成員"+hobby); 7 } 8 }
若是想要調用非靜態成員咱們能夠建立對象來調用他:方法
1 public class HelloWorld{ 2 static String name = "hello"; 3 String hobby = "hello"; 4 public static void main(String [] args){ 5 System.out.println("同類中能夠直接調用靜態成員"+name); 6 HelloWorld hello = new HelloWorld(); 7 System.out.println("不能夠直接調用非靜態成員"+hello.hobby); 8 } 9 }
2.在普通成員方法中,既能夠直接使用靜態成員變量也能夠直接使用非靜態成員變量:
1 public class HelloWorld{ 2 static String name = "hello"; 3 String hobby = "hello"; 4 public void show(){ 5 System.out.println("同類中能夠直接調用靜態成員"+name); 6 System.out.println("能夠直接調用非靜態成員"+hobby); 7 8 } 9 }
1 public class HelloWorld{ 2 String name; 3 //經過初始化塊給成員變量賦值 4 { 5 name = "我愛Java"; 6 } 7 }
在類的聲明中,能夠包含多個初始化塊,當建立類的實例時,就會依次執行這些代碼塊。若是使用 static 修飾初始化塊,就稱爲靜態初始化塊。
1 public class HelloWorld{ 2 static String name; 3 //靜態初始化代碼塊 4 static{ 5 name = "我愛Java"; 6 } 7 }
須要特別注意:靜態初始化塊只在類加載時執行,且只會執行一次,同時靜態初始化塊只能給靜態變量賦值,不能初始化普通的成員變量。
咱們來看一段代碼:
1 public class HelloWorld{ 2 int num1; 3 int num2; 4 static int num3; 5 public HelloWorld(){ 6 num1 = 91; 7 System.out.println("經過構造方法爲變量num1賦值!"); 8 } 9 {//初始化塊 10 num2 = 81; 11 System.out.println("經過初始化塊爲變量num2賦值!"); 12 } 13 static { 14 num3 = 56; 15 System.out.println("經過靜態初始化塊爲靜態變量num3賦值!"); 16 } 17 public static void main(String [] args){ 18 HelloWorld hello = new HelloWorld(); 19 System.out.println("num1:"+hello.num1); 20 System.out.println("num2:"+hello.num2); 21 System.out.println("num3:"+num3); 22 HelloWorld hello2 = new HelloWorld(); 23 } 24 }
運行結果:
經過靜態初始化塊爲靜態變量num3賦值!
經過初始化塊爲變量num2賦值!
經過構造方法爲變量num1賦值!
num1:91
num2:81
num3:56
經過初始化塊爲變量num2賦值!
經過構造方法爲變量num1賦值!
經過輸出結果,咱們能夠看到,程序運行時靜態初始化塊最早被執行,而後執行普通初始化塊,最後才執行構造方法。因爲靜態初始化塊只在類加載時執行一次,因此當再次建立對象 hello2 時並未執行靜態初始化塊。