封裝: Encapsulation
用private關鍵字將不想被外界訪問到的屬性和方法隱藏起來
封裝對於類的開發者和使用者都有好處:
對於類的開發者:
能夠讓數據得到保密,得到隱藏,從而更加安全
對於類的使用者:
能夠讓使用者將精力 全部集中在覈心業邏輯上
類的開發應當 高內聚 低耦合
內聚:獨立完成功能的能力, 自強不息,自己的事情自己做
耦合:模塊與模塊之間的依賴關係
Java當中封裝怎麼實現解耦:
所有的屬性都應當使用private修飾
並且提供兩個public的方法 setters 和 getters
設置屬性的 用於得到屬性的
*封裝可以給設置和得到屬性一種統一的方式,有助於代碼的解耦
*封裝可以讓程序員重新拿回主動權,讓程序員來決定,是否需要用戶設置和得到屬性
*利用反射 我們可以動態的解析一個類的屬性 然後根據規範 得到它的getter和setter方法 從而動態的去設置一個屬性或得到一個屬性
*所有的方法應當考慮:
一個方法究竟是給外界提供的核心方法還是給核心方法服務的方法
核心方法用public修飾
給核心方法提供服務的方法應當用private對外屏蔽
public class TestEncap {
public static void main(String[] args){
Student stu = new Student();
stu.SetName("Tom");//設置屬性
stu.setAge(19);
System.out.println(stu.getName()+"|"+stu.getAge());
}
}
class Student{
//private 訪問控制權限修飾符,只能在本類中訪問
private String name;
private int age;
//設置屬性的方法 setter
public void SetName(String name){
this.name = name;
}
//得到屬性的方法 getter
public String getName(){//提供了一種統一得到屬性的方法
return name;
}
public void setAge(int age){
this.age = age;
}
public int getAge(){
return age;
}
}
繼承: Inherit
用extends關鍵字 建立兩個類之間 is a 的關係 = 是一個 是一種
java當中的類只有單根繼承,但接口可以多重繼承
關於私有屬性 能不能被繼承,有沒有繼承,算不算繼承
私有屬性在子類當中是切實存在的,它是由於java創建對象的流程所決定的
但是不能繼續直接使用了,因此不能算作繼承得到的
private 訪問控制權限修飾符,歸根結底是一個修飾符,有沒有和能不能被訪問是完全不同的兩個概念
*:在你日後寫代碼的每一天當中,只要涉及到代碼重用 應當考慮使用繼承實現,當然還有其它很多種方式可以實現
public class TestInherit{
public static void main(String[] args){
Student stu = new Student();
stu.eat();
stu.sleep();
}
}
class People{
String name;
public void eat(){
System.out.println("People類的eat方法");
}
public void sleep(){
System.out.println("People類的sleep方法");
}
}
class Student extends People{
//在這裏 可以通過繼承得到People類的所有方法 前提:需要public修飾的
}
多態: Polymorphism
靜態多態:指的是編譯時多態 java當中的方法重載
動態多態:指的是運行時多態
一個對象總有多種稱呼它的類型 - 一個事物總有多種形態
多態需要注意什麼:
對象在內存當中是客觀存在的 不會因爲改變稱呼它的類型而發生任何變化,當你在調用方法的時候,真正方法執行哪個方法 取決於你new的是什麼類型的對象
但是編譯器看等號左邊的類型來進行語法檢查
public class TestPoly{
public static void main(String[] args){
Animal cat = new Cat();//父類類型 = new 子類對象 多態
cat.eat();
}
}
class Animal{
public void eat(){
System.out.println("Animal中的eat方法");
}
}
class Cat extends Animal{
public void eat(){
System.out.println("cat 類的eat方法");
}
}
動態多態的出現肯定會伴隨着一種語法:
父類類型 = new 子類對象
接口類型 = new 實現類對象
public class TestPoly{
public static void main(String[] args){
Machine m = new Machine();
Car c = new Car();
m.run();
c.run();
m = c;//m = new Car(); 多態
m.run();
}
}
class Machine{
public void run(){
System.out.println("這是機器運轉的方法");
}
}
class Car extends Machine{
public void run(){
System.out.println("這是汽車開動方法");
}
}
方法重載:(方法過載)
Overload / Overloading
放生在同一個類型當中
1.方法名字必須相同
2.返回類型可能不同
*3.參數列表必須不同
參數類型不同 可以算作不同
參數個數不同 可以算作不同
參數順序不同 可以算作不同
*參數名字不同不能算作不同
*形參的名字不會在.class文件中保存,只會以代號的形式保存
*判讀兩個方法是否滿足重載時 最關鍵的是參數列表必須不一樣,另外還是必須要在同一個類中,方法名且必須一樣
//測試方法重載
public class TesrOverload {
public static void main(String[] args){
/*什麼情況下使用重載? 我想讓一個方法實用性更強 功能更強大
System類的out屬性時PrintStrema類的對象 println方法被重載了N次
System.out.println(5);//int
System.out.println("Hello");//String
System.out.println(true);//boolean
System.out.println('e');//char
*/
A aa = new A();
aa.show();//調用無參的
aa.show(5);//調用形參int數的
}
}
class A{
//方法重載,也是靜態多態
public void show(){
System.out.println("show 1");
}
public void show(int num){
System.out.println("show 2");
}
}
方法覆蓋:(方法重寫)
Override
發生在有繼承關係的父類和子類之間 而且是發生在子類類型當中的
子類繼承得到父類的方法之後 覺得方法實現已經不滿足我們程序的要求了,然後重新給出了實現
*靜態方法能否被覆蓋:
靜態方法只是對其進行了隱藏,並沒有覆蓋
方法覆蓋 要求符合<進化論> - 物競天擇,適者生存
方法的修飾符 方法簽名部分 = 返回類型+方法名+參數列表 異常部分
public void showInteger(int args)throws Exception{}
不能越小 必須完全相同 不能更廣泛
方法的修飾符:子類的方法應該比父類的方法更加優秀的,更加優秀的方法就應該讓更多的類型可以使用,所以 方法修飾符絕對不允許越變越小 可以是相同的
方法簽名部分:除了形參的名字,其他部分必須完全相同
異常部分: 拋出的異常不能更廣泛
方法如果越變越優秀,那麼決不允許蘊藏着更多的隱患,所以子類拋出的異常必須是父類拋出異常的子類類型
//方法覆蓋
public class TestOverride {
public static void main(String[] args){
After60 a90 = new After90();//多態
a90.research();
}
}
class After60{
public void research(){//研究新實物的方法
System.out.println("去圖書館查閱資料 / 打電話諮詢");
}
}
class After90 extends After60{
public void research(){
super.research();//super代表父類對象 調用父類類型的research方法
System.out.println("有問題找Google || 度娘");
}
}