1. 程式人生 > 其它 >遞推演算法題:令人費解的開關『拉燈』

遞推演算法題:令人費解的開關『拉燈』

1.static存在的意義

1.static可以建立獨立於具體域物件的變數或者方法,這個方法或者變數不與包含它所對應的類的任何物件包含在一起。也就是說即使沒有建立物件,也可以呼叫這個變數或者方法

2.static可以用來形成靜態程式碼塊來優化程式效能。static塊可以存放在類的任何一個地方,當類進行載入時,會按照static塊的順序來進行載入,並且只會載入一次

3.static可以為某特定域分配單一儲存空間,而不去考慮究竟要建立多少物件,甚至根本就不建立物件。(一個static欄位對每個類來說都只有一份儲存空間,而非static欄位則是對每個物件都有一個儲存空間

2.static的特點

1.被static修飾的變數或者方法獨立於該類的任何物件,可以理解成這些變數或者方法不屬於任何一個例項物件,是被類中所有物件所共享。

2.在一個類第一次載入的時候,就會載入static修飾的部分,而且只在類第一次使用時載入並進行初始化。

3.static變數值在第一次載入的時候就分配了空間,以後建立物件時不會再進行重新分配空間,但是可以賦值。

4.被static修飾的變數或者方法是優先於物件的,也就是說,即使你沒有建立物件,也可以呼叫static修飾的變數或者方法。

3.static的應用場景

3.1修飾成員變數

成員變數是可以被類中所有物件所共享的,當一個成員變數被static所修飾,那麼這個變數就成了靜態變數

靜態變數和例項變數有點區別,首先沒有被static修飾的成員變數叫做例項變數,例項變數屬於這個類的例項物件,也就是說,可以通過建立物件來對它進行呼叫。兩者之間的區別是,靜態變數不屬於任何例項物件,它是屬於類的。在類載入的時候進行分配一次記憶體空間。例項變數是每次建立物件時,都會為成員變數分配記憶體空間。

3.2修飾成員方法

被static修飾的方法叫做靜態方法,其實main方法就是一個靜態方法。靜態方法可以直接被呼叫,也就是類名.方法名()的方式。

3.3靜態程式碼塊

也就是在類中被static包裹的一部分程式碼,形如static{}

public class staticTest {
   
public staticTest(){ System.out.println("staticTest:構造器初始化"); } { System.out.println("staticTest:初始化塊"); } static { System.out.println("staticTest:靜態初始化塊"); } } class staticTest1 extends staticTest{ public staticTest1(){ System.out.println("staticTest1:構造器初始化"); } { System.out.println("staticTest1:初始化塊"); } static { System.out.println("staticTest1:靜態初始化塊"); } } class staticTest2 extends staticTest1{ public staticTest2(){ System.out.println("staticTest2:構造器初始化"); } { System.out.println("staticTest2:初始化塊"); } static { System.out.println("staticTest2:靜態初始化塊"); } } class staticTest3 extends staticTest2{ public static void main(String[] args) { staticTest2 staticTest2 = new staticTest2(); System.out.println("------"); staticTest staticTest = new staticTest2(); } }

輸出:

"C:\Program Files\JetBrains\IntelliJ IDEA 2019.3.3\jbr\bin\java.exe" "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2019.3.3\lib\idea_rt.jar=65088:C:\Program Files\JetBrains\IntelliJ IDEA 2019.3.3\bin" -Dfile.encoding=UTF-8 -classpath D:\java\javase進階\.idea\out\production\Test staticTest3
staticTest:靜態初始化塊
staticTest1:靜態初始化塊
staticTest2:靜態初始化塊
staticTest:初始化塊
staticTest:構造器初始化
staticTest1:初始化塊
staticTest1:構造器初始化
staticTest2:初始化塊
staticTest2:構造器初始化
------
staticTest:初始化塊
staticTest:構造器初始化
staticTest1:初始化塊
staticTest1:構造器初始化
staticTest2:初始化塊
staticTest2:構造器初始化

Process finished with exit code 0

可以看出:靜態程式碼塊只初始化一次。

3.4靜態內部類

1.靜態內部類不可以訪問外部類非靜態成員。

2.靜態內部類不需要建立外部類的物件就可以訪問。

3.靜態內部類可以有多種許可權訪問型別。

public class Myself {
    private static String name = "業平";
    private String sex = "男";

    //靜態內部類可以為public修飾
    public static class Person{
        //靜態內部類可以定義非靜態變數
        private String address = "山東";

        private static String high = "180";

        //內部類公用成員
        public String age = "20";

        public void disPlay(){
            //不能訪問外部類非靜態成員
            //System.out.println(sex);

            //可以訪問靜態成員
            System.out.println(name);

            //訪問本內部類成員
            System.out.println(address);
        }
    }
    public void play(){
        //外部類訪問內部類非靜態成員需要例項化
        Person person = new Person();
        person.disPlay();

        //System.out.println(high);
        //System.out.println(age);

        System.out.println(person.age);
        System.out.println(person.address);
    }

    public static void main(String[] args) {
        Myself myself = new Myself();
        myself.play();
    }
}

輸出:

業平
山東
20
山東