1. 程式人生 > 資訊 >小米天然氣衛士開啟眾籌:支援遠端自檢、洩漏報警,首發 169 元

小米天然氣衛士開啟眾籌:支援遠端自檢、洩漏報警,首發 169 元

方法的組成

函式,也可以稱作方法:用於抽取、封裝某一段功能程式碼

public static void main(String[] args) {
   
}
修飾符 返回值 函式名(引數列表) {
   函式體
}

一個標準的函式由以下幾個部分組成

  • 修飾符:表示不同的目的,例如 publicstatic
  • 返回值型別:宣告該函式的返回值型別,可以不存在返回值,寫作 void
  • 函式名:函式的名稱
  • 引數列表:宣告該函式呼叫時可以接收的引數,可以是原始型別、引用型別
  • 函式體:函式中具體的程式碼塊
  • 返回值:函式執行後產生的結果

方法的引數傳遞

在函式的呼叫過程中,可以同時傳入若干個任意型別的引數

對於傳入的引數,也分為原始型別、引用型別兩類

整數、浮點數、字元,或者引用型別的陣列、自定義類,都是可以的

值得注意的是,在 Java 中,函式的引數傳遞,只存在值傳遞

值傳遞:引數傳遞時,形參接收的是實參的實際資料的拷貝副本

引用傳遞:引數傳遞時,形參接收的是實參的引用地址的拷貝副本

Java 的引數傳遞極易混淆,而 Java 官方已經定義,Java 中只存在值傳遞

Java 就是值傳遞,只不過是將物件的引用當做值傳遞給方法,即值傳遞中的按引用傳遞

值傳遞示例(原始型別):

public static void main(String[] args) {
    int a = 10;
    int b = 20;
    set(a, b);
    System.out.println("=====");
    System.out.println(a);
    System.out.println(b);
    /* 20、10、=====、10、20 */
}

public static void set(int a, int b) {
    a = 20;
    b = 10;
    System.out.println(a);
    System.out.println(b);
}

值傳遞示例(引用型別):

public static void main(String[] args) {
    int[] ints = {1, 2};
    System.out.println(Arrays.toString(ints));
    set(ints);
    System.out.println(Arrays.toString(ints));
    /* [1, 2]、[2, 2] */
}

public static void set(int[] array) {
    array[0] = 2;
}

在上述的兩個示例中,原始型別的傳參,實際引數不受形參變化的影響,不做考慮

而對於引用引數的傳遞,形參的修改,實參也隨之修改,看似不符合值傳遞的定義

當傳遞的是引用型別,拷貝的副本是物件的引用地址

簡單的理解,形參得到實參的拷貝副本,間接的獲得引用地址,可以修改堆記憶體的資料

值傳遞的引用型別,在此刻,與引用傳遞十分相似

不同的是,真正的引用傳遞,形參是直接獲得引用地址,並可以對該地址做出修改

上圖,是關於值傳遞、引用傳遞的簡單說明,真正意義上的引用傳遞,可以參考 Rust 語言,講述清晰

在值傳遞中,引用物件 2 獲得的僅僅是堆記憶體地址的拷貝副本,只存在訪問、修改堆記憶體資料的許可權

而在引用傳遞中,引用物件 2 直接獲得了堆記憶體的 root 許可權,可以直接修改其引用地址

姑且,將值傳遞再細分為按值傳遞、按引用傳遞

只需要牢記兩點

  • 值傳遞,形參儘可以修改內容
  • 引用傳遞,形參可以修改引用地址

在 Java 中,只存在值傳遞,且傳遞的是引用地址的拷貝,僅可以操作記憶體資料

方法的可變長引數

當函式的 傳入引數數目不確定 時,可以使用 可變長引數 進行定義,例如排序方法

以下程式碼是關乎可變長引數的使用案例

public static void main(String[] args) {
    get(12, 12, 23, 34, 45, 34, 23);
}

public static void get(int... a) {
    System.out.println(Arrays.toString(a));
}

對於可變長引數的使用,需要注意兩點:

  1. 可變長引數必須放在引數列表的末位
  2. 一個函式的引數列表,僅可以存在一個可變長引數

方法的可變長引數,實質上就是陣列的體現,建議使用陣列物件進行傳參,也更易於理解

public void get(int[] a, String[] b) {}

函式的引數列表中,兩個 不同型別的可變長引數也不可以共存,而陣列可以做到

方法的過載

當類中,存在多個同名方法時,這就是方法過載的體現

函式過載:過載僅是 方法名的相同,引數列表、訪問修飾符、返回值型別可以不同

以下是方法過載的程式碼示例

public static void main(String[] args) {
    get((byte) 1);
    Integer integer = get((short) 1);
    get(1);
    get((long) 1);
}

private static void get(byte... a) {
    System.out.println("byte");
}

public static Integer get(short... a) {
    System.out.println("short");
    return 0;
}

public static void get(int... a) {
    System.out.println("int");
}

public static void get(long... a) {
    System.out.println("long");
}

值得注意的是,不可以存在引數列表相同的過載函式

簡單的理解,函式名同名,引數列表不同

方法的遞迴呼叫

遞迴函式,簡單的理解,就是自己呼叫自己的函式

下列是函式的遞迴呼叫,求階乘

public static void main(String[] args) {
    System.out.println(get(5));
}

public static int get(int a) {
    if (a == 0) {
        return 1;
    } else {
        return a * get(a - 1);
    }
}

步驟如下

  • get(5) = 5 * get(4)
  • get(4) = 4 * get(3)
  • get(3) = 3 * get(2)
  • get(2) = 2 * get(1)
  • get(1) = 1 * get(0)
  • get(0) = 1

計算得出,get(5) 的最終結果為 120