網(wǎng)站優(yōu)化設(shè)計方案怎么做青島運營網(wǎng)絡(luò)推廣業(yè)務(wù)
7. 類和對象
- 7.1 面向?qū)ο蟮某醪秸J(rèn)知
- 7.1.1 什么是面向?qū)ο?/li>
- 7.1.2 面向?qū)ο笈c面向過程
- 7.2 類定義和使用
- 7.2.1 簡單認(rèn)識類
- 7.2.2 類的定義格式
- 7.2.3 定義一個狗類
- 7.2.4 定義一個學(xué)生類
- 7.3 類的實例化
- 7.3.1 什么是實列化
- 7.3.2 引用只能指向?qū)ο?#xff0c;且不能同時指向多個對象
- 7.3.3 類和對象的說明
- 例題:如何交換兩個數(shù)據(jù)
- 7.4this引用
- 7.4.1 為什么要有this引用
- 7.4.2 什么是this引用
- 7.4.3 this引用特性
- 7.5 對象的構(gòu)造及初始化
- 7.5.1 如何初始化對象
- 7.5.2 默認(rèn)初始化
- 7.5.3 就地初始化
- 7.5.4 構(gòu)造方法
- 概念:
- 特性
- 一旦這個類 提供了 任何一種構(gòu)造方法 編譯器 都將不會再為你提供 不帶參數(shù)的構(gòu)造方法。
- 快捷鍵構(gòu)造幾個參數(shù)的構(gòu)造方法
- 構(gòu)造方法中,可以通過this調(diào)用其他構(gòu)造方法來簡化代碼
7.1 面向?qū)ο蟮某醪秸J(rèn)知
7.1.1 什么是面向?qū)ο?/h3>
Java是一門純面向?qū)ο蟮恼Z言(Object Oriented Program,簡稱OOP),在面向?qū)ο蟮氖澜缋?#xff0c;一切皆為對象。面向?qū)ο笫墙鉀Q問題的一種思想,主要依靠對象之間的交互完成一件事情。用面向?qū)ο蟮乃枷雭砩婕俺绦?#xff0c;更符合人們對事物的認(rèn)知,對于大型程序的設(shè)計、擴展以及維護都非常友好。
7.1.2 面向?qū)ο笈c面向過程
- 傳統(tǒng)洗衣服過程:
傳統(tǒng)的方式:注重的是洗衣服的過程,少了一個環(huán)節(jié)可能都不行。
而且不同衣服洗的方式,時間長度,擰干方式都不同,處理起來就比較麻煩。如果將來要洗鞋子,那就是另一種放方式。
按照該種方式來寫代碼,將來擴展或者維護起來會比較麻煩。 - 現(xiàn)代洗衣服過程:
以面向?qū)ο蠓绞絹磉M行處理,就不關(guān)注洗衣服的過程,具體洗衣機是怎么來洗衣服,如何來甩干的,用戶不用去關(guān)心,只需要將衣服放進洗衣機,倒入洗衣粉,啟動開關(guān)即可,通過對象之間的交互來完成的。
7.2 類定義和使用
面相對象程序設(shè)計關(guān)注的是對象,比如洗衣機。
7.2.1 簡單認(rèn)識類
類是用來對一個實體(對象)來進行描述的,主要描述該實體(對象)具有哪些屬性(外觀尺寸等),哪些功能(用來干啥)
7.2.2 類的定義格式
//WashMachine 類名 采用大駝峰命名 我們自己定義的類型
class WashMachine {//屬性 , 字段, 成員變量 , 這些成員變量是定義在方法外部 類的內(nèi)部public String brand; // 品牌public String type; // 型號public String weight; // 重量public String length; // 長public String width; // 寬public String height; // 高public String color; // 顏色//成員方法public void washClothes() { //洗衣服System.out.println("洗衣服功能");}public void dryClothes() { //脫水System.out.println("脫水功能");}public void setTime() { //定時System.out.println("定時功能");}
}
7.2.3 定義一個狗類
class PetDog {public String name;//名字public String color;//顏色public int age;//年齡// 狗的屬性public void barks() {System.out.println(name + ": 旺旺旺~~~");}// 狗的行為public void wag() {System.out.println(name + ": 搖尾巴~~~");}
}
7.2.4 定義一個學(xué)生類
class Student{public String name;public String gender;public short age;public double score;public void DoClass(){}public void DoHomework(){}public void Exam(){}
}
注意:
- 一般一個文件當(dāng)中只定義一個類
- main方法所在的類一般要使用public修飾(注意:Eclipse默認(rèn)會在public修飾的類中找main方法)
- public修飾的類必須要和文件名相同
- 不要輕易去修改public修飾的類的名稱,如果要修改,通過開發(fā)工具修改class名字即可修改。
7.3 類的實例化
7.3.1 什么是實列化
定義了一個類,就相當(dāng)于在計算機中定義了一種新的類型,與int,double類似,只不過int和double是java語言自帶的內(nèi)置類型,而類是用戶自定義了一個新的類型,比如上述的:PetDog類和Student類。它們都是類(一種新定義的類型)有了這些自定義的類型之后,就可以使用這些類來定義實例(或者稱為對象)。
用類類型創(chuàng)建對象的過程,稱為類的實例化,在Java中采用new關(guān)鍵字,配合類名來實例化對象。
class Dog {public String name;//名字public String color;//顏色public int age;//年齡// 狗的屬性public void barks() {System.out.println(name + ": 旺旺旺~~~");}// 狗的行為public void wag() {System.out.println(name + ": 搖尾巴~~~");}
}
public class ClassObject {public static void main(String[] args) {Dog dog1 = new Dog();dog1.name = "阿黃";dog1.age = 2;dog1.color = "黃色";System.out.println("年齡:"+dog1.age);System.out.println("姓名:"+dog1.name);System.out.println("顏色:"+dog1.color);dog1.barks();dog1.wag();System.out.println();Dog dog2 = new Dog();dog2.name = "旺財";dog2.age = 3;dog2.color = "黑色";System.out.println("年齡:"+dog2.age);System.out.println("姓名:"+dog2.name);System.out.println("顏色:"+dog2.color);dog2.barks();dog2.wag();//可以通過new 關(guān)鍵字 來實例化多個對象Dog dog3 = new Dog();Dog dog4 = new Dog();Dog dog5 = new Dog();}
}
注意:
- new 關(guān)鍵字用于創(chuàng)建一個對象的實例.
- 使用 . 來訪問對象中的屬性和方法.
- 同一個類可以創(chuàng)建對個實例.
7.3.2 引用只能指向?qū)ο?#xff0c;且不能同時指向多個對象
引用只能存儲一個對象的地址;
Dog dog2 = null;代表 Dog2這個引用 不指向任何對象,而不是指向null。
7.3.3 類和對象的說明
- 類只是一個模型一樣的東西,用來對一個實體進行描述,限定了類有哪些成員.
- 類是一種自定義的類型,可以用來定義變量.
- 一個類可以實例化出多個對象,實例化出的對象 占用實際的物理空間,存儲類成員變量
- 做個比方。類實例化出對象就像現(xiàn)實中使用建筑設(shè)計圖建造出房子,類就像是設(shè)計圖,只設(shè)計出需要什么東西,但是并沒有實體的建筑存在,同樣類也只是一個設(shè)計,實例化出的對象才能實際存儲數(shù)據(jù),占用物理空間
例題:如何交換兩個數(shù)據(jù)
調(diào)用swap方法后:
class Myvalue {public int val;
}public class Test {public static void swap(Myvalue val1,Myvalue val2) {int tmp = val1.val;val1.val = val2.val;val2.val = tmp;}public static void main(String[] args) {Myvalue myValue1 = new Myvalue();myValue1.val = 10;Myvalue myValue2 = new Myvalue();myValue2.val = 20;System.out.println("交換前:"+myValue1.val);System.out.println("交換前:"+myValue2.val);swap(myValue1,myValue2);System.out.println("交換后:"+myValue1.val);System.out.println("交換后:"+myValue2.val);}
}
7.4this引用
7.4.1 為什么要有this引用
public class Date {public int year;public int month;public int day;//局部變量優(yōu)先使用public void setDate(int year,int month,int day) {year = year;month = month;day = day;}public void printDate() {System.out.println("年:"+year+"月:"+month+"日:"+day);}public static void main(String[] args) {Date date = new Date();date.setDate(1945,9,1);date.printDate();}
}
當(dāng)形參名不小心與成員變量名相同時:局部變量會優(yōu)先使用,把年月日直接賦值為0。
7.4.2 什么是this引用
this引用指向當(dāng)前對象(成員方法運用時調(diào)用該成員方法的對象),在成員方法中所有成員變量的操作,都是通過該引用去訪問。只不過所有的操作對用戶是透明的,即用戶不需要來傳遞,編譯器自動完成。
public class Date {public int year;public int month;public int day;//局部變量優(yōu)先使用,誰調(diào)用當(dāng)前這個方法,誰就是thispublic void setDate(int year,int month,int day) {this.year = year;this.month = month;this.day = day;}public void printDate() {System.out.println("年:"+this.year+"月:"+this.month+"日:"+this.day);}public static void main(String[] args) {Date date = new Date();date.setDate(1945,9,1);date.printDate();Date date2 = new Date();date2.setDate(1949,10,1);date2.printDate();}
}
7.4.3 this引用特性
- this的類型:對應(yīng)類類型引用,即哪個對象調(diào)用就是哪個對象的引用類型
- this只能在"成員方法"中使用
- 在"成員方法"中,this只能引用當(dāng)前對象,不能再引用其他對象
- this是“成員方法”第一個隱藏的參數(shù),編譯器會自動傳遞,在成員方法執(zhí)行時,編譯器會負(fù)責(zé)將調(diào)用成員方法對象的引用傳遞給該成員方法,this負(fù)責(zé)來接收
在代碼層面,下圖右側(cè)中的Date類也是可以通過編譯的
this.成員變量 --> 訪問成員變量
this.func() – > 訪問當(dāng)前的成員方法
public void func() {System.out.println("hahah");}public void printDate() {System.out.println("年:"+this.year+"月:"+this.month+"日:"+this.day);this.func();}
this() – > 調(diào)用當(dāng)前類的構(gòu)造方法
7.5 對象的構(gòu)造及初始化
7.5.1 如何初始化對象
在Java方法內(nèi)部定義一個局部變量時,必須要初始化,否則會編譯失敗。
public static void main(String[] args) {
int a;
System.out.println(a);
}
// Error:(26, 28) java: 可能尚未初始化變量a
要讓上述代碼通過編譯,非常簡單,只需在正式使用a之前,給a設(shè)置一個初始值即可。如果是對象:
public static void main(String[] args) {Date d = new Date();d.printDate();d.setDate(2021,6,9);d.printDate();
}
需要調(diào)用之前寫的SetDate方法才可以將具體的日期設(shè)置到對象中。通過上述例子發(fā)現(xiàn)兩個問題:
- 每次對象創(chuàng)建好后調(diào)用SetDate方法設(shè)置具體日期,比較麻煩,那對象該如何初始化?
- 局部變量必須要初始化才能使用,為什么字段聲明之后沒有給值依然可以使用?
7.5.2 默認(rèn)初始化
在上文中提出的第二個問題:為什么局部變量在使用時必須要初始化,而成員變量可以不用呢?
public class Date {public int year;public int month;public int day;public Date(int year, int month, int day) {// 成員變量在定義時,并沒有給初始值, 為什么就可以使用呢?System.out.println(this.year);System.out.println(this.month);System.out.println(this.day);}public static void main(String[] args) {// 此處a沒有初始化,編譯時報錯:// Error:(24, 28) java: 可能尚未初始化變量a// int a;// System.out.println(a);Date d = new Date(2021,6,9);}
}
對于 Date d = new Date(2021,6,9); 在JVM中做了很多事情如下:
- 檢測對象對應(yīng)的類是否加載了,如果沒有加載則加載
- 為對象分配內(nèi)存空間
- 處理并發(fā)安全問題
比如:多個線程同時申請對象,JVM要保證給對象分配的空間不沖突 - 初始化所分配的空間
即:對象空間被申請好之后,對象中包含的成員已經(jīng)設(shè)置好了初始值,比如
7.5.3 就地初始化
就是在聲明成員變量時,就直接給出了初始值。
public class Date {public int year = 1900;public int month = 1;public int day = 1;public Date() {}public Date(int year, int month, int day) {}public static void main(String[] args) {Date d1 = new Date(2021,6,9);Date d2 = new Date();}
}
7.5.4 構(gòu)造方法
概念:
構(gòu)造方法(也稱為構(gòu)造器)是一個特殊的成員方法,該方法沒有返回值,名字必須與類名相同,在創(chuàng)建對象時,由編譯器自動調(diào)用,并且在整個對象的生命周期內(nèi)只能調(diào)用一次。
public class Date {public int year;public int month;public int day;// 構(gòu)造方法:// 名字與類名相同,沒有返回值類型,設(shè)置為void也不行// 一般情況下使用public修飾// 在創(chuàng)建對象時由編譯器自動調(diào)用,并且在對象的生命周期內(nèi)只調(diào)用一次public Date(int year, int month, int day){this.year = year;this.month = month;this.day = day;System.out.println("Date(int,int,int)方法被調(diào)用了");}public void printDate(){System.out.println(year + "-" + month + "-" + day);}public static void main(String[] args) {// 此處創(chuàng)建了一個Date類型的對象,并沒有顯式調(diào)用構(gòu)造方法Date d = new Date(2021,6,9); // 輸出Date(int,int,int)方法被調(diào)用了d.printDate(); // 2021-6-9}
}
注意:構(gòu)造方法的作用就是對對象中的成員進行初始化,并不負(fù)責(zé)給對象開辟空間。
特性
- 名字必須與類名相同
- 沒有返回值類型,設(shè)置為void也不行
- 創(chuàng)建對象時由編譯器自動調(diào)用,并且在對象的生命周期內(nèi)只調(diào)用一次(相當(dāng)于人的出生,每個人只能出生一次)
- 構(gòu)造方法可以重載(用戶根據(jù)自己的需求提供不同參數(shù)的構(gòu)造方法)
public class Date {public int year;public int month;public int day;boolean flg;String name;public Date() {this.year = 2008;this.month = 8;this.day = 8;//this(2008,8,8); // 必須放到 當(dāng)前構(gòu)造方法的第一行 不能形成環(huán)System.out.println("執(zhí)行了不帶參數(shù)的構(gòu)造方法");}public Date(int year,int month,int day) {this.year = year;this.month = month;this.day = day;System.out.println("執(zhí)行了帶三個參數(shù)的構(gòu)造方法");}public void printDate() {System.out.println("年:"+this.year+"月:"+this.month+"日:"+this.day);
/* this.func();System.out.println(flg);System.out.println(name);*/}public static void main(String[] args) {Date date = new Date();Date date2 = new Date(2008,1,1);/* date.setDate(1945,9,1);date.printDate();*//* Date date2 = new Date();date2.setDate(1949,10,1);date2.printDate();*/}
}
名字相同,參數(shù)列表不同,因此構(gòu)成了方法重載。
構(gòu)造方法至少有1個。也就是說當(dāng)你沒有寫任何的構(gòu)造方法時,Java會自帶一個不帶參數(shù)的構(gòu)造方法。
對象的初始化一定會 調(diào)用構(gòu)造方法。
對象的產(chǎn)生 簡單來說一定會有2步:
- 為對象分配內(nèi)存
- 調(diào)用合適的構(gòu)造方法
一旦這個類 提供了 任何一種構(gòu)造方法 編譯器 都將不會再為你提供 不帶參數(shù)的構(gòu)造方法。
把下面這段刪了,然后Date date = new Date();就會報錯,也就是當(dāng)你有了任何一種構(gòu)造方法,編譯器就不會提供不帶參數(shù)的構(gòu)造方法。
public Date() {
/* this.year = 2008;this.month = 8;this.day = 8;*/this(2008,8,8); // 必須放到 當(dāng)前構(gòu)造方法的第一行 不能形成環(huán)System.out.println("執(zhí)行了不帶參數(shù)的構(gòu)造方法");}
快捷鍵構(gòu)造幾個參數(shù)的構(gòu)造方法
構(gòu)造方法中,可以通過this調(diào)用其他構(gòu)造方法來簡化代碼
public Date() {
/* this.year = 2008;this.month = 8;this.day = 8;*/this(2008,8,8); // 必須放到 當(dāng)前構(gòu)造方法的第一行 不能形成環(huán)System.out.println("執(zhí)行了不帶參數(shù)的構(gòu)造方法");}