static關鍵字的作用主要是實現某個方法或屬性與類相關而不是與對象相關,主要有4種使用情況:成員變量,成員方法,代碼塊和內部類。
1.static關鍵字修飾成員變量
package test; public class staticAttributeTest { /* * 局部變量:局部變量是寫在類中具體的方法里的; * 成員變量:是在類中定義的變量,包括用static修飾的靜態變量和不用static修飾的實例變量; * * 實例變量(全局變量):在類中定義的沒有static修飾的變量,實例變量只有實例化對象之后才可以使用,每當實例化一個對象, * * 會創建一個副本並初始化,各個對象中的實例變量的修改互不影響; * static: * 1.實現某個方法或屬性與類關聯而不是與對象關聯,這樣就可以在不創建對象的情況下通過類來直接調用方法或使用類的屬性; * staticInt是被類擁有的,任意一個對象修改它的值,都會引起該值的變化。而nonStaticInt為實例變量,只有創建對象之后才可以調用, * 為該對象自己的值,只能對象修改自己的實例變量的值;不同的對象對該值的修改互不影響; * */ public static int staticInt=0; public int nonStaticInt=0; public static void main(String[] args){ staticAttributeTest t=new staticAttributeTest(); System.out.println(t.staticInt); //0 System.out.println(staticAttributeTest.staticInt); //0 System.out.println(t.nonStaticInt); //0 t.staticInt++; t.nonStaticInt++; staticAttributeTest t1=new staticAttributeTest(); staticAttributeTest t2=new staticAttributeTest(); //靜態變量只有一個,被類擁有,存儲在方法區中,所有對象共享這個靜態變量; System.out.println(t1.staticInt); //1 System.out.println(t2.staticInt); //1 System.out.println(staticAttributeTest.staticInt); //1 //實例變量是與具體對象相關的 /* * 所有的實例變量、引用變量的地址都存在棧內存中,對象本身及對象的數據成員都存在堆內存中 * */ System.out.println(t1.nonStaticInt); //0 t1.nonStaticInt++; System.out.println(t1.nonStaticInt); //1 System.out.println(t2.nonStaticInt); //0 } }
2.static成員方法
static修飾的方法是類的方法,不需要創建對象就可以直接調用,而非static方法是對象的方法,只有對象被創建出來后才可以被調用。static方法不能調用非static方法,也不能訪問非static類型的變量(非static的只有創建對象才可以調用和訪問,static都沒有對象)。
static方法中也不能使用this和super關鍵字,在java中使用this來引用當前對象,使用super引用父類的成分。
this關鍵字的作用:https://www.cnblogs.com/bluetree2/p/10784375.html
super關鍵字的作用:https://www.cnblogs.com/bluetree2/p/10784962.html
3.static代碼塊
static代碼塊不在任何一個方法內,可以置於類中的任何地方,類中可以有多個static塊。在類初次被加載的時候,會按照static塊的順序來執行每個static塊,並且只會執行一次。
package test; class FatherClass { public int value; public void f() { value=100; System.out.println("父類的value屬性值="+value); } public FatherClass(){ System.out.println("FatherClass constructor"); } } class ChildClass extends FatherClass { /** * 子類除了繼承父類所具有的value屬性外,自己又另外聲明了一個value屬性, * 也就是說,此時的子類擁有兩個value屬性。 */ public ChildClass(){ super(); System.out.println("ChildClass constructor"); } public int value; /** * 在子類ChildClass里面重寫了從父類繼承下來的f()方法里面的實現,即重寫了f()方法的方法體。 */ public void f() { //使用super作為父類對象的引用對象來調用父類對象里面的f()方法 //這個value是子類自己定義的那個value,不是從父類繼承下來的那個value value=200; super.f(); //父類的value屬性值=100 System.out.println("子類的value屬性值="+value); //子類的value屬性值=200 //打印出來的是子類自定義的那個value的值,這個值是200 System.out.println(value); //200 System.out.println(super.value); //100 } } public class SuperKeyTest { static{ System.out.println("static block1"); } public static void main(String[] args) { ChildClass cc = new ChildClass(); cc.f(); } static{ System.out.println("static block2"); } }
執行結果:
static block1 static block2 FatherClass constructor ChildClass constructor 父類的value屬性值=100 子類的value屬性值=200 200 100