Java關(guān)鍵字列表如下,包含50個(gè)關(guān)鍵并炮,所有字符都是小寫(xiě)
https://docs.oracle.com/javase/tutorial/java/nutsandbolts/_keywords.html
基本類型
先介紹基本類型關(guān)鍵字如下
有關(guān)基本類型的解釋默刚,主要是整形byte/short/int/long,浮點(diǎn)float/double逃魄,字符型char, 布爾值boolean荤西,參考解釋https://blog.csdn.net/qwe969153746/article/details/53353534
注意:Java浮點(diǎn)數(shù)默認(rèn)是double, 整形默認(rèn)是int,另外有一個(gè)常量池的緩存也需要注意邪锌,還有Integer.valueof()方法是Integer a = 10語(yǔ)句的默認(rèn)賦值方法勉躺。
/**
* 8種基本類型的包裝類和對(duì)象池
* 包裝類:java提供的為原始數(shù)據(jù)類型的封裝類,如:int(基本數(shù)據(jù)類型)觅丰,Integer封裝類饵溅。
* 對(duì)象池:為了一定程度上減少頻繁創(chuàng)建對(duì)象,將一些對(duì)象保存到一個(gè)"容器"中妇萄。
*
* Byte,Short,Integer,Long,Character蜕企。這5種整型的包裝類的對(duì)象池范圍在-128~127之間,也就是說(shuō)冠句,
* 超出這個(gè)范圍的對(duì)象都會(huì)開(kāi)辟自己的堆內(nèi)存轻掩。
*
* Boolean也實(shí)現(xiàn)了對(duì)象池技術(shù)。Double,Float兩種浮點(diǎn)數(shù)類型的包裝類則沒(méi)有實(shí)現(xiàn)懦底。
* String也實(shí)現(xiàn)了常量池技術(shù)唇牧。
*
* 自動(dòng)裝箱拆箱技術(shù)
* JDK5.0及之后允許直接將基本數(shù)據(jù)類型的數(shù)據(jù)直接賦值給其對(duì)應(yīng)地包裝類。
* 如:Integer i = 3;(這就是自動(dòng)裝箱)
* 實(shí)際編譯代碼是:Integer i=Integer.valueOf(3); 編譯器自動(dòng)轉(zhuǎn)換
* 自動(dòng)拆箱則與裝箱相反:int i = (Integer)5;
*/
public class Test {
public static void main(String[] args) {
//基本數(shù)據(jù)類型常量池范圍-128~127
Integer n1 = -129;
Integer n2 = -129;
Long n3 = 100L;
Long n4 = 100L;
Double n5 = 12.0;
Double n6 = 12.0;
//false
System.out.println(n1 == n2);
//true
System.out.println(n3 == n4);
//false
System.out.println(n5 == n6);
//String常量池技術(shù),注意:這里String不是用new創(chuàng)建的對(duì)象
String str1 = "abcd";
String str2 = "abcd";
//true
System.out.println(str1 == str2);
}
}
//5種整形的包裝類Byte,Short,Integer,Long,Character的對(duì)象聚唐,
//在值小于127時(shí)可以使用常量池
Integer i1=127;
Integer i2=127;
System.out.println(i1==i2)//輸出true
//值大于127時(shí)丐重,不會(huì)從常量池中取對(duì)象
Integer i3=128;
Integer i4=128;
System.out.println(i3==i4)//輸出false
//Boolean類也實(shí)現(xiàn)了常量池技術(shù)
Boolean bool1=true;
Boolean bool2=true;
System.out.println(bool1==bool2);//輸出true
//浮點(diǎn)類型的包裝類沒(méi)有實(shí)現(xiàn)常量池技術(shù)
Double d1=1.0;
Double d2=1.0;
System.out.println(d1==d2)//輸出false
char 字符
Java語(yǔ)言的一個(gè)關(guān)鍵字,用來(lái)定義一個(gè)字符類型 杆查。short 短的
Java語(yǔ)言的關(guān)鍵字扮惦,用來(lái)定義一個(gè)short類型的變量。int 整數(shù)類型
Java(TM)的一個(gè)關(guān)鍵字根灯,用來(lái)定義一個(gè)整形變量
Java(TM)的一個(gè)關(guān)鍵字径缅,用來(lái)定義一系列的方法和常量。它可以被類實(shí)現(xiàn)烙肺,通過(guò)implements關(guān)鍵字纳猪。long 長(zhǎng)整型
Java語(yǔ)言的一個(gè)關(guān)鍵字,用來(lái)定義一個(gè)long類型的變量桃笙。float 浮點(diǎn)數(shù)
一個(gè)Java語(yǔ)言的關(guān)鍵字氏堤,用來(lái)定義一個(gè)浮點(diǎn)數(shù)變量 。double 雙精度型
一個(gè)Java語(yǔ)言的關(guān)鍵字搏明,用來(lái)定義一個(gè)double類型的變量 鼠锈。
以下是條件分支和循環(huán)語(yǔ)句關(guān)鍵字
for 為了(循環(huán)語(yǔ)句)
一個(gè)Java語(yǔ)言的關(guān)鍵字,用來(lái)聲明一個(gè)循環(huán)星著。程序員可以指定要循環(huán)的語(yǔ)句购笆,推出條件和初始化變量。if 如果
Java編程語(yǔ)言的一個(gè)關(guān)鍵字虚循,用來(lái)生成一個(gè)條件測(cè)試同欠,如果條件為真样傍,就執(zhí)行if下的語(yǔ)句。else 否則
一個(gè)Java語(yǔ)言的關(guān)鍵字铺遂,如果if語(yǔ)句的條件不滿足就會(huì)執(zhí)行該語(yǔ)句衫哥。break 跳出
一個(gè)Java的關(guān)鍵字,用來(lái)改變程序執(zhí)行流程襟锐,立刻從當(dāng)前語(yǔ)句的下一句開(kāi)始執(zhí)行從撤逢。如果后面跟有一個(gè)標(biāo)簽,則從標(biāo)簽對(duì)應(yīng)的地方開(kāi)始執(zhí)行 粮坞。case 實(shí)例
Java語(yǔ)言的關(guān)鍵字蚊荣,用來(lái)定義一組分支選擇,如果某個(gè)值和switch中給出的值一樣捞蚂,就會(huì)從該分支開(kāi)始執(zhí)行妇押。continue 繼續(xù)
一個(gè)Java的關(guān)鍵字跷究,用來(lái)打斷當(dāng)前循環(huán)過(guò)程姓迅,從當(dāng)前循環(huán)的最后重新開(kāi)始執(zhí)行,如果后面跟有一個(gè)標(biāo)簽俊马,則從標(biāo)簽對(duì)應(yīng)的地方開(kāi)始執(zhí)行丁存。do
一個(gè)Java語(yǔ)言的關(guān)鍵字,用來(lái)聲明一個(gè)循環(huán)柴我,這個(gè)循環(huán)的結(jié)束條件可以通過(guò)while關(guān)鍵字設(shè)置while 一會(huì)兒(循環(huán)語(yǔ)句)
Java語(yǔ)言的一個(gè)關(guān)鍵字解寝,用來(lái)定義一段反復(fù)執(zhí)行的循環(huán)語(yǔ)句。循環(huán)的退出條件是while語(yǔ)句的一部分艘儒。關(guān)于break和continue聋伦。
continue語(yǔ)句與break語(yǔ)句相關(guān),但較少用到界睁。continue語(yǔ)句用于使其所在的for觉增、while或do-while語(yǔ)句開(kāi)始下一次循環(huán)。在while與do-while語(yǔ)句中翻斟,continue語(yǔ)句的執(zhí)行意味著立即執(zhí)行測(cè)試部分逾礁;在for循環(huán)語(yǔ)句中,continue語(yǔ)句的執(zhí)行則意味著使控制傳遞到增量部分访惜。
以下是異常處理機(jī)制
- try catch finally原理:
http://www.blogjava.net/fancydeepin/archive/2012/07/08/java_try-catch-finally.html
java 的異常處理中嘹履,
在不拋出異常的情況下,程序執(zhí)行完 try 里面的代碼塊之后债热,該方法并不會(huì)立即結(jié)束砾嫉,而是繼續(xù)試圖去尋找該方法有沒(méi)有 finally 的代碼塊,
如果沒(méi)有 finally 代碼塊窒篱,整個(gè)方法在執(zhí)行完 try 代碼塊后返回相應(yīng)的值來(lái)結(jié)束整個(gè)方法焕刮;
如果有 finally 代碼塊蚓峦,此時(shí)程序執(zhí)行到 try 代碼塊里的 return 語(yǔ)句之時(shí)并不會(huì)立即執(zhí)行 return,而是先去執(zhí)行 finally 代碼塊里的代碼济锄,
若 finally 代碼塊里沒(méi)有 return 或沒(méi)有能夠終止程序的代碼暑椰,程序?qū)⒃趫?zhí)行完 finally 代碼塊代碼之后再返回 try 代碼塊執(zhí)行 return 語(yǔ)句來(lái)結(jié)束整個(gè)方法;
若 finally 代碼塊里有 return 或含有能夠終止程序的代碼荐绝,方法將在執(zhí)行完 finally 之后被結(jié)束一汽,不再跳回 try 代碼塊執(zhí)行 return。
在拋出異常的情況下低滩,原理也是和上面的一樣的召夹,你把上面說(shuō)到的 try 換成 catch 去理解就 OK 了 _
try catch jvm原理:
https://blog.csdn.net/TellH/article/details/70940757#t0
throw 投、拋
Java語(yǔ)言的關(guān)鍵字恕沫,允許用戶拋出一個(gè)exception對(duì)象或者任何實(shí)現(xiàn)throwable的對(duì)象
throws 聲明拋棄異常
Java語(yǔ)言的關(guān)鍵字监憎,用在方法的聲明中來(lái)說(shuō)明哪些異常這個(gè)方法是不處理的,而是提交到程序的更高一層婶溯。try 嘗試鲸阔、審判
Java語(yǔ)言的關(guān)鍵字,用來(lái)定義一個(gè)可能拋出異常語(yǔ)句塊迄委。如果一個(gè)異常被拋出褐筛,一個(gè)可選的catch語(yǔ)句塊會(huì)處理try語(yǔ)句塊中拋出的異常。同時(shí)叙身,一個(gè)finally語(yǔ)句塊會(huì)被執(zhí)行渔扎,無(wú)論一個(gè)異常是否被拋出。catch 捕捉
Java的一個(gè)關(guān)鍵字信轿,用來(lái)聲明當(dāng)try語(yǔ)句塊中發(fā)生運(yùn)行時(shí)錯(cuò)誤或非運(yùn)行時(shí)異常時(shí)運(yùn)行的一個(gè)塊晃痴。finally 最后
一個(gè)Java語(yǔ)言的關(guān)鍵字,用來(lái)執(zhí)行一段代碼不管在前面定義的try語(yǔ)句中是否有異巢坪觯或運(yùn)行時(shí)錯(cuò)誤發(fā)生倘核。
package test;
//jdk 1.8
public class TestException1 {
/**
* catch中的return和throw是不能共存的(無(wú)論誰(shuí)先誰(shuí)后都編譯不通過(guò))
* 如果只throw e,則必須try-catch捕捉異常e或用throws拋出異常e
* 如果只return 定罢,則在catch段正常返回值
*/
int testEx0(){
boolean ret = true;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return 0;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = false;
return -1;
throw e;
}
}
/**
* 在finally中的return和throw是不能共存的(無(wú)論誰(shuí)先誰(shuí)后都編譯不通過(guò))
* 如果只throw e笤虫,則必須try-catch捕捉異常e或用throws拋出異常e
* 如果只return ,則在catch段正常返回值
*/
int testEx00(){
int ret = 0;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return ret;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = -1;
}finally{
ret = 1;
System.out.println("testEx, finally; return value=" + ret);
throw e;
return ret;
}
}
/**
* 結(jié)果:
testEx, catch exception
testEx, finally; return value=false
false
結(jié)論:在finally里沒(méi)有return的時(shí)候:先執(zhí)行finally的語(yǔ)句祖凫,再執(zhí)行catch的return
*/
boolean testEx01(){
boolean ret = true;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return true;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = false;
return ret;
}finally{
System.out.println("testEx, finally; return value=" + ret);
}
}
/**
* 結(jié)果:
* testEx, catch exception
testEx, finally; return value=1
1
結(jié)論:在finally里有return的時(shí)候:先執(zhí)行finally的語(yǔ)句和return琼蚯,忽略catch的return
*/
int testEx02(){
int ret = 0;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return ret;
} catch (Exception e) {
ret = -1;
System.out.println("testEx, catch exception");
return ret;
}finally{
ret = 1;
System.out.println("testEx, finally; return value=" + ret);
return ret;
}
}
/**
* 編譯能通過(guò),
* 但運(yùn)行時(shí)拋異常(當(dāng)然也沒(méi)有返回值)
* @return
*/
boolean testEx03(){
boolean ret = true;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return true;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = false;
throw e;
}finally{
System.out.println("testEx, finally; return value=" + ret);
}
}
/**
* 編譯不能通過(guò)(必須加throws主動(dòng)拋異常惠况,或try-catch捕捉遭庶,)
* 但運(yùn)行時(shí)拋異常(當(dāng)然也沒(méi)有返回值)
* @return
* @throws Exception
*/
boolean testEx031(){
boolean ret = true;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return true;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = false;
throw new Exception(e);
}finally{
System.out.println("testEx, finally; return value=" + ret);
}
}
/**
* 結(jié)果:
* testEx, catch exception
testEx, finally; return value=1
1
結(jié)論:
函數(shù)在finally里正常返回return的值,無(wú)異常稠屠,顯然catch中的throw被忽略
*/
int testEx04(){
int ret = 0;
try {
int c = 12 / 0;
System.out.println("testEx,successfully");
return ret;
} catch (Exception e) {
System.out.println("testEx, catch exception");
ret = -1;
throw e;
}finally{
ret = 1;
System.out.println("testEx, finally; return value=" + ret);
return ret;
}
}
public static void main(String[] args) {
try {
System.out.println(new TestException1().testEx0());
//System.out.println(new TestException1().testEx00());
//System.out.println(new TestException1().testEx01());
//System.out.println(new TestException1().testEx02());
//System.out.println(new TestException1().testEx03());
//System.out.println(new TestException1().testEx031());
//System.out.println(new TestException1().testEx04());
} catch (Exception e) {
e.printStackTrace();
}
}
}
以下是類或這變量的權(quán)限控制
private 私有的
Java語(yǔ)言的一個(gè)關(guān)鍵字峦睡,用在方法或變量的聲中翎苫。它表示這個(gè)方法或變量只能被這個(gè)類的其它元素所訪問(wèn)。protected 保護(hù)類型
Java語(yǔ)言的一個(gè)關(guān)鍵字榨了,在方法和變量的聲明中使用煎谍,它表示這個(gè)方法或變量只能被同一個(gè)類中的,子類中的或者同一個(gè)包中的類中的元素所訪問(wèn)龙屉。public 公共的
Java語(yǔ)言的一個(gè)關(guān)鍵字呐粘,在方法和變量的聲明中使用,它表示這個(gè)方法或變量能夠被其它類中的元素訪問(wèn)转捕。
以下修飾字段變量的關(guān)鍵字
final 最終作岖、不可更改的
一個(gè)Java語(yǔ)言的關(guān)鍵字。你只能定義一個(gè)實(shí)體一次五芝,以后不能改變它或繼承它痘儡。更嚴(yán)格的講:一個(gè)final修飾的類不能被子類化,一個(gè)final修飾的方法不能被重寫(xiě)枢步,一個(gè)final修飾的變量不能改變其初始值沉删。volatile 揮發(fā)性、易揮發(fā)的
Java語(yǔ)言的關(guān)鍵字价捧,用在變量的聲明中表示這個(gè)變量是被同時(shí)運(yùn)行的幾個(gè)線程異步修改的丑念。
volatile是一個(gè)類型修飾符(type specifier)涡戳。它是被設(shè)計(jì)用來(lái)修飾被不同線程訪問(wèn)和修改的變量结蟋。如果沒(méi)有volatile,基本上會(huì)導(dǎo)致這樣的結(jié)果:要么無(wú)法編寫(xiě)多線程程序渔彰,要么編譯器失去大量?jī)?yōu)化的機(jī)會(huì)嵌屎。static 靜態(tài)的
Java語(yǔ)言的關(guān)鍵字,用來(lái)定義一個(gè)變量為類變量恍涂。類只維護(hù)一個(gè)類變量的拷貝宝惰,不管該類當(dāng)前有多少個(gè)實(shí)例。"static" 同樣能夠用來(lái)定義一個(gè)方法為類方法再沧。類方法通過(guò)類名調(diào)用而不是特定的實(shí)例尼夺,并且只能操作類變量。transient 短暫的炒瘸、瞬時(shí)的
Java語(yǔ)言的關(guān)鍵字淤堵,用來(lái)表示一個(gè)域不是該對(duì)象串行化的一部分。當(dāng)一個(gè)對(duì)象被串行化的時(shí)候顷扩,transient型變量的值不包括在串行化的表示中拐邪,然而非transient型的變量是被包括進(jìn)去的。
synchronized同步控制
簡(jiǎn)單來(lái)說(shuō)原理是
synchronized修飾對(duì)象或類
重量級(jí)鎖也就是通常說(shuō)synchronized的對(duì)象鎖隘截,鎖標(biāo)識(shí)位為10扎阶,其中指針指向的是monitor對(duì)象(在 Synchronized 代碼塊中的監(jiān)視器 )的起始地址汹胃。每個(gè)對(duì)象都存在著一個(gè) monitor 與之關(guān)聯(lián),對(duì)象與其 monitor 之間的關(guān)系有存在多種實(shí)現(xiàn)方式东臀,如 monitor 可以與對(duì)象一起創(chuàng)建銷毀或當(dāng)線程試圖獲取對(duì)象鎖時(shí)自動(dòng)生成着饥,但當(dāng)一個(gè) monitor 被某個(gè)線程持有后,它便處于鎖定狀態(tài)惰赋。 有monitorenter和monitorexit的操作-
synchronized修飾方法
當(dāng)方法調(diào)用時(shí)贱勃,調(diào)用指令將會(huì) 檢查方法的 ACC_SYNCHRONIZED 訪問(wèn)標(biāo)志是否被設(shè)置,如果設(shè)置了谤逼,執(zhí)行線程將先持有 monitor 贵扰, 然后再執(zhí)行方法,最后再方法完成(無(wú)論是正常完成還是非正常完成)時(shí)釋放monitor
- 輕量級(jí)鎖和重量級(jí)鎖
輕量級(jí)鎖流部。他的基本思想是戚绕,當(dāng)線程要獲取鎖時(shí)把鎖對(duì)象的 Mark Word 復(fù)制一份到當(dāng)前線程的棧頂,然后執(zhí)行一個(gè) CAS 操作把鎖對(duì)象的 Mark Word 更新為指向棧頂?shù)母北镜闹羔樦剑绻晒t當(dāng)前線程擁有了鎖舞丛。
偏向鎖。獲取的過(guò)程如下果漾,當(dāng)鎖對(duì)象第一次被線程獲取的時(shí)候球切,虛擬機(jī)把對(duì)象頭中的標(biāo)志位設(shè)為“01”,即偏向模式绒障。同時(shí)使用CAS操作把獲取到這個(gè)鎖的線程的ID記錄在對(duì)象的Mark Word之中的偏向線程ID吨凑,并將是否偏向鎖的狀態(tài)位置置為1。如果CAS操作成功户辱,持有偏向鎖的線程以后每次進(jìn)入這個(gè)鎖相關(guān)的同步塊時(shí)鸵钝,直接檢查ThreadId是否和自身線程Id一致,如果一致庐镐,則認(rèn)為當(dāng)前線程已經(jīng)獲取了鎖恩商,虛擬機(jī)就可以不再進(jìn)行任何同步操作(例如Locking、Unlocking及對(duì)Mark Word的Update等)必逆。
詳見(jiàn)原理: http://www.reibang.com/p/ce4f5e43e0a8?utm_campaign=haruki&utm_content=note&utm_medium=reader_share&utm_source=weixin
其他關(guān)鍵字
this 這個(gè)
Java語(yǔ)言的關(guān)鍵字怠堪,用來(lái)代表它出現(xiàn)的類的一個(gè)實(shí)例。this可以用來(lái)訪問(wèn)類變量和類方法名眉。void 空
Java語(yǔ)言的關(guān)鍵字粟矿,用在Java語(yǔ)言的方法聲明中說(shuō)明這個(gè)方法沒(méi)有任何返回值。"void"也可以用來(lái)表示一句沒(méi)有任何功能的語(yǔ)句璧针。
return 返回
Java語(yǔ)言的一個(gè)關(guān)鍵字嚷炉,用來(lái)結(jié)束一個(gè)方法的執(zhí)行。它后面可以跟一個(gè)方法聲明中要求的值探橱。import 導(dǎo)入
Java(TM)編程語(yǔ)言的一個(gè)關(guān)鍵字申屹,在源文件的開(kāi)始部分指明后面將要引用的一個(gè)類或整個(gè)包衡查,這樣就不必在使用的時(shí)候加上包的名字签餐。implements 實(shí)現(xiàn)
Java(TM)編程語(yǔ)言的一個(gè)關(guān)鍵字跑杭,在類的聲明中是可選的瞻想,用來(lái)指明當(dāng)前類實(shí)現(xiàn)的接口。 tm=tradeMark(Java商標(biāo)的意思)Abstract 抽象的
一個(gè)Java語(yǔ)言中的關(guān)鍵字杆煞,用在類的聲明中來(lái)指明一個(gè)類是不能被實(shí)例化的魏宽,但是可以被其它類繼承。一個(gè)抽象類可以使用抽象方法决乎,抽象方法不需要實(shí)現(xiàn)队询,但是需要在子類中被實(shí)現(xiàn) 。
多態(tài)實(shí)現(xiàn)原理參考:
從虛擬機(jī)角度看Java多態(tài)->(重寫(xiě)override)的實(shí)現(xiàn)原理
https://www.cnblogs.com/2014asm/p/8633660.html
前面對(duì)jvm 的vtable 進(jìn)行了研究和驗(yàn)證构诚,再總結(jié)下特點(diǎn):
- vtable 分配在 instanceKlass對(duì)象實(shí)例的內(nèi)存末尾 蚌斩。
- 其實(shí)vtable可以看作是一個(gè)數(shù)組,數(shù)組中的每一項(xiàng)成員元素都是一個(gè)指針范嘱,指針指向 Java 方法在 JVM 內(nèi)部所對(duì)應(yīng)的 method 實(shí)例對(duì)象的內(nèi)存首地址 送膳。
- vtable是 Java 實(shí)現(xiàn)面向?qū)ο蟮亩鄳B(tài)性的機(jī)制,如果一個(gè) Java 方法可以被繼承和重寫(xiě)丑蛤, 則最終通過(guò) put_method_at函數(shù)將方法地址替換,完成 Java 方法的動(dòng)態(tài)綁定叠聋。
4.Java 子類會(huì)繼承父類的 vtable,Java 中所有類都繼承自 java.lang.Object, java .lang.Object 中有 5 個(gè)虛方法(可被繼承和重寫(xiě)):
void finalize()
boolean equals(Object)
String toString()
int hashCode()
Object clone()
因此受裹,如果一個(gè) Java 類中不聲明任何方法碌补,則其 vtalbe 的長(zhǎng)度默認(rèn)為 5 。
5.Java 類中不是每一個(gè) Java 方法的內(nèi)存地址都會(huì)保存到 vtable 表中名斟,只有當(dāng) Java子類中聲明的 Java 方法是 public 或者 protected 的脑慧,且沒(méi)有 final 、 static 修飾砰盐,并且 Java 子類中的方法并非對(duì)父類方法的重寫(xiě)時(shí), JVM 才會(huì)在 vtable 表中為該方法增加一個(gè)引用 坑律。
6.如果 Java 子類某個(gè)方法重寫(xiě)了父類方法岩梳,則子類的vtable 中原本對(duì)父類方法的指針會(huì)被替換成子類對(duì)應(yīng)的方法指針,調(diào)用put_method_at函數(shù)替換vtable中對(duì)應(yīng)的方法指針晃择。
- instanceof 判斷對(duì)象類型
一個(gè)二操作數(shù)的Java(TM)語(yǔ)言關(guān)鍵字冀值,用來(lái)測(cè)試第一個(gè)參數(shù)的運(yùn)行時(shí)類型是否和第二個(gè)參數(shù)兼容。
instance of 原理: https://cloud.tencent.com/developer/article/1079376
JavaSE 8 instanceof 的實(shí)現(xiàn)算法:https://docs.oracle.com/javase/specs/jvms/se8/html/jvms-6.html#jvms-6.5.instanceof
</figure>
1宫屠、obj如果為null列疗,則返回false;否則設(shè)S為obj的類型對(duì)象浪蹂,剩下的問(wèn)題就是檢查S是否為T的子類型抵栈;
2告材、如果S == T,則返回true古劲;
3斥赋、接下來(lái)分為3種情況,之所以要分情況是因?yàn)閕nstanceof要做的是“子類型檢查”产艾,而Java語(yǔ)言的類型系統(tǒng)里數(shù)組類型疤剑、接口類型與普通類類型三者的子類型規(guī)定都不一樣,必須分開(kāi)來(lái)討論闷堡。
①隘膘、S是數(shù)組類型:如果 T 是一個(gè)類類型,那么T必須是Object杠览;如果 T 是接口類型棘幸,那么 T 必須是由數(shù)組實(shí)現(xiàn)的接口之一;
②倦零、接口類型:對(duì)接口類型的 instanceof 就直接遍歷S里記錄的它所實(shí)現(xiàn)的接口误续,看有沒(méi)有跟T一致的;
③扫茅、類類型:對(duì)類類型的 instanceof 則是遍歷S的super鏈(繼承鏈)一直到Object蹋嵌,看有沒(méi)有跟T一致的。遍歷類的super鏈意味著這個(gè)算法的性能會(huì)受類的繼承深度的影響葫隙。