1. 程式人生 > 實用技巧 >學習java的第二週

學習java的第二週

面向物件基礎

  • class好比是人類,instance好比是指定的某個人

  • person型別,類似於C語言中的結構體

方法(看的不是很懂,感覺思路不清晰)

  • 一個class可以包含多個field(field即為領域,private私有域,protected保護域,public公共域,publicstatic公共靜態域)
  • 直接操作field容易造成邏輯混亂,我們可以用private修飾field,拒絕外部訪問,但是可以、使用方法(method)來讓外部程式碼可以間接修改field:

public方法

public class Main {
    public static void main(String[] args) {
        Person ming = new Person();
        ming.setName("Xiao Ming"); // 設定name
        ming.setAge(12); // 設定age
        System.out.println(ming.getName() + ", " + ming.getAge());
    }
}

class Person {
    private String name;
    private int age;

    public String getName() {
        return this.name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return this.age;
    }

    public void setAge(int age) {
        if (age < 0 || age > 100) {
            throw new IllegalArgumentException("invalid age value");
        }
        this.age = age;
    }
}
  • 呼叫方法setName()setAge()來間接修改private欄位,方法返回值通過return語句實現,如果沒有返回值,返回型別設定為void,可以省略return

private方法

public class Main {
    public static void main(String[] args) {
        Person ming = new Person();
        ming.setBirth(2008);
        System.out.println(ming.getAge());
    }
}

class Person {
    private String name;
    private int birth;

    public void setBirth(int birth) {
        this.birth = birth;
    }

    public int getAge() {
        return calcAge(2019); // 呼叫private方法
    }

    // private方法:
    private int calcAge(int currentYear) {
        return currentYear - this.birth;
    }
}
  • calcAge()是一個private方法,外部程式碼無法呼叫,但是,內部方法getAge()可以呼叫它
  • Person類只定義了birth欄位,沒有定義age欄位,獲取age時,通過方法getAge()返回的是一個實時計算的值,並非儲存在某個欄位的值

this變數

  • 在方法內部,可以使用一個隱含的變數this,它始終指向當前例項,通過this.field就可以訪問當前例項的欄位,如果沒有命名衝突,可以省略this

方法引數

  • 方法可以包含0個或任意個引數。方法引數用於接收傳遞給方法的變數值。呼叫方法時,必須嚴格按照引數的定義一一傳遞
class Person {
    ...
    public void setNameAndAge(String name, int age) {
        ...
    }
}
  • 呼叫這個setNameAndAge()方法時,必須有兩個引數,且第一個引數必須為String,第二個引數必須為int

可變引數

  • 可變引數用型別...定義,可變引數相當於陣列型別
class Group {
    private String[] names;

    public void setNames(String... names) {
        this.names = names;
    }
}
  • 上面的setNames()就定義了一個可變引數,完全可以把可變引數改寫為String[]型別(需要自己先構造)
class Group {
    private String[] names;

    public void setNames(String[] names) {
        this.names = names;
    }
}

構造方法

預設構造方法

  • 如果一個類沒有定義構造方法,編譯器會自動為我們生成一個預設構造方法,它沒有引數,也沒有執行語句
class Person {
    public Person() {
    }
}
  • 沒有在構造方法中初始化欄位時,引用型別的欄位預設是null,數值型別的欄位用預設值,int型別預設值是0,布林型別預設值是false

在Java中,建立物件例項的時候,按照如下順序進行初始化

class Person {
    private String name = "Unamed";
    private int age = 10;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }
}
  • 先初始化欄位,例如,int age = 10;表示欄位初始化為10double salary;表示欄位預設初始化為0String name;表示引用型別欄位預設初始化為null
  • 執行構造方法的程式碼進行初始化。

多構造方法

  • 可以定義多個構造方法,在通過new操作符呼叫的時候,編譯器通過構造方法的引數數量、位置和型別自動區分
class Person {
    private String name;
    private int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public Person(String name) {
        this.name = name;
        this.age = 12;
    }

    public Person() {
    }
}
  • 如果呼叫new Person("Xiao Ming", 20);,會自動匹配到構造方法public Person(String, int)
  • 如果呼叫new Person("Xiao Ming");,會自動匹配到構造方法public Person(String)
  • 如果呼叫new Person();,會自動匹配到構造方法public Person()

方法過載

  • 在一個類中,我們可以定義多個方法。如果有一系列方法,它們的功能都是類似的,只有引數有所不同,那麼,可以把這一組方法名做成同名方法
class Hello {
    public void hello() {
        System.out.println("Hello, world!");
    }

    public void hello(String name) {
        System.out.println("Hello, " + name + "!");
    }

    public void hello(String name, int age) {
        if (age < 18) {
            System.out.println("Hi, " + name + "!");
        } else {
            System.out.println("Hello, " + name + "!");
        }
    }
}
  • 方法名相同,但各自的引數不同,稱為方法過載Overload