J2SE基礎(chǔ)~2
開心一刻:不要羨慕別人栽燕,幸福其實(shí)就是一碗白開水鹃骂,你每天都在喝秸侣,不要羨慕別人喝的飲料有各種顏色存筏,其實(shí)未必有你的白開水解渴!有這么一則寓言:“豬說假如讓我再活一次味榛,我要做一頭牛椭坚,工作雖然累點(diǎn),但名聲好搏色,讓人愛憐善茎;牛說加入讓我再活一次,我要做一頭豬频轿,吃罷睡垂涯,睡罷吃,不出力航邢,不流汗耕赘,活得賽神仙;鷹說假如讓我再活一次膳殷,我要做一只雞操骡,渴了有水,餓了有米,有房住当娱,還受人保護(hù)吃既;雞說假如讓我再活一次考榨,我要做一只鷹跨细,可以翱翔天空,云游四海河质,任意捕兔殺雞”冀惭。幸福如人飲水,冷暖自知掀鹅。你不是我散休,怎知我走過的路?怎知我心中的苦與樂乐尊?所以戚丸,真的不必去羨慕別人。明白自己所擁有的扔嵌,想清楚自己真正想要的限府,才會(huì)真正快樂。扯了這么多還是看文章吧痢缎,想必你來這里也不是看我扯淡的胁勺,哈哈~ ~ !
下面正式進(jìn)入干貨區(qū),喜歡的話独旷、雙擊署穗、評(píng)論、轉(zhuǎn)發(fā)嵌洼,動(dòng)一動(dòng)你的小手讓更多的人知道案疲!關(guān)注帥比~楊
HashMap和ConcurrentHashMap的區(qū)別,HashMap的底層源碼麻养。
TreeMap络拌、HashMap、LindedHashMap的區(qū)別回溺。
Collection包結(jié)構(gòu)與Collections的區(qū)別春贸。
try catch finally,try里有return遗遵,finally還執(zhí)行么萍恕?
Excption與Error包結(jié)構(gòu)。OOM你遇到過哪些情況车要,SOF你遇到過哪些情況允粤。
Java面向?qū)ο蟮娜齻€(gè)特征與含義。
Override和Overload的含義及區(qū)別。
interface與abstract類的區(qū)別类垫。
static class 與non static class的區(qū)別司光。
java多態(tài)的實(shí)現(xiàn)原理。
實(shí)現(xiàn)多線程的兩種方法:Thread與Runable悉患。
線程同步的方法:sychronized残家、lock、reentrantLock等售躁。
鎖的等級(jí):方法鎖坞淮、對(duì)象鎖、類鎖陪捷。
寫出生產(chǎn)者消費(fèi)者模式回窘。
ThreadLocal的設(shè)計(jì)理念與作用。
ThreadPool用法與優(yōu)勢(shì)市袖。
Concurrent包里的其他東西:ArrayBlockingQueue啡直、CountDownLatch等等。
wait()和sleep()的區(qū)別苍碟。
foreach與正常for循環(huán)效率對(duì)比酒觅。
Java IO與NIO。
反射的作用與原理驰怎。
泛型常用特點(diǎn)阐滩,List能否轉(zhuǎn)為L(zhǎng)ist。
解析XML的幾種方式的原理與特點(diǎn):DOM县忌、SAX掂榔、PULL。
Java與C++對(duì)比症杏。
Java1.7與1.8新特性装获。
設(shè)計(jì)模式:?jiǎn)卫⒐S厉颤、適配器穴豫、責(zé)任鏈、觀察者等等逼友。
JNI的使用精肃。
1. HashMap和ConcurrentHashMap的區(qū)別,HashMap的底層源碼帜乞。
HashMap
底層數(shù)組+鏈表實(shí)現(xiàn)司抱,可以存儲(chǔ)null鍵和null值,線程不安全初始size為16黎烈,擴(kuò)容:newsize = oldsize*2习柠,size一定為2的n次冪擴(kuò)容針對(duì)整個(gè)Map匀谣,每次擴(kuò)容時(shí),原來數(shù)組中的元素依次重新計(jì)算存放位置资溃,并重新插入元素后才判斷該不該擴(kuò)容武翎,有可能無效擴(kuò)容(插入后如果擴(kuò)容,如果沒有再次插入溶锭,就會(huì)產(chǎn)生無效擴(kuò)容)當(dāng)Map中元素總數(shù)超過Entry數(shù)組的75%宝恶,觸發(fā)擴(kuò)容操作,為了減少鏈表長(zhǎng)度暖途,元素分配更均勻計(jì)算index方法:index = hash & (tab.length - 1)ConcurrentHashMap底層采用分段的數(shù)組+鏈表實(shí)現(xiàn)卑惜,線程安全通過把整個(gè)Map分為N個(gè)Segment膏执,可以提供相同的線程安全驻售,但是效率提升N倍,默認(rèn)提升16倍更米。(讀操作不加鎖欺栗,由于HashEntry的value變量是 volatile的,也能保證讀取到最新的值征峦。)
Hashtable的synchronized是針對(duì)整張Hash表的迟几,即每次鎖住整張表讓線程獨(dú)占,ConcurrentHashMap允許多個(gè)修改操作并發(fā)進(jìn)行栏笆,其關(guān)鍵在于使用了鎖分離技術(shù)类腮。有些方法需要跨段,比如size()和containsValue()蛉加,它們可能需要鎖定整個(gè)表而而不僅僅是某個(gè)段蚜枢,這需要按順序鎖定所有段,操作完畢后针饥,又按順序釋放所有段的鎖厂抽。擴(kuò)容:段內(nèi)擴(kuò)容(段內(nèi)元素超過該段對(duì)應(yīng)Entry數(shù)組長(zhǎng)度的75%觸發(fā)擴(kuò)容,不會(huì)對(duì)整個(gè)Map進(jìn)行擴(kuò)容)丁眼,插入前檢測(cè)需不需要擴(kuò)容筷凤,有效避免無效擴(kuò)容
2. TreeMap、HashMap苞七、LindedHashMap的區(qū)別藐守。
Map: 在數(shù)組中我們是通過數(shù)組下標(biāo)來對(duì)其內(nèi)容索引的,而在Map中我們通過對(duì)象來對(duì)對(duì)象進(jìn)行索引蹂风,用來索引的對(duì)象叫做key卢厂,其對(duì)應(yīng)的對(duì)象叫做value。這就是我們平時(shí)說的鍵值對(duì)硫眨。
HashMap 是一個(gè)最常用的Map,它根據(jù)鍵的HashCode 值存儲(chǔ)數(shù)據(jù),根據(jù)鍵可以直接獲取它的值足淆,具有很快的訪問速度巢块。HashMap最多只允許一條記錄的鍵為Null;允許多條記錄的值為Null,且不支持線程的同步巧号,即任一時(shí)刻可以有多個(gè)線程同時(shí)寫HashMap族奢,可能會(huì)導(dǎo)致數(shù)據(jù)的不一致。如果需要同步丹鸿,可以用Collections的synchronizedMap方法使HashMap具有同步的能力越走。
LinkedHashMap是Map接口的哈希表和鏈接列表實(shí)現(xiàn),具有可預(yù)知的迭代順序靠欢。此實(shí)現(xiàn)提供所有可選的映射操作廊敌,并允許使用null值和null鍵。此類不保證映射的順序门怪,特別是它不保證該順序恒久不變骡澈。 LinkedHashMap實(shí)現(xiàn)與HashMap的不同之處在于,后者維護(hù)著一個(gè)運(yùn)行于所有條目的雙重鏈接列表掷空。此鏈接列表定義了迭代順序肋殴,該迭代順序可以是插入順序或者是訪問順序。 注意坦弟,此實(shí)現(xiàn)不是同步的护锤。如果多個(gè)線程同時(shí)訪問鏈接的哈希映射,而其中至少一個(gè)線程從結(jié)構(gòu)上修改了該映射酿傍,則它必須保持外部同步烙懦。
TreeMap 不僅可以保持順序,而且可以用于排序赤炒;HashMap通常比TreeMap快一點(diǎn)(樹和哈希表的數(shù)據(jù)結(jié)構(gòu)使然)氯析,建議多使用HashMap,在需要排序的Map時(shí)候才用TreeMap可霎。
3. Collection包結(jié)構(gòu)與Collections的區(qū)別魄鸦。
Collection是集合類的上級(jí)接口,子接口主要有Set 和List癣朗。
Collections是針對(duì)集合類的一個(gè)幫助類拾因,提供了操作集合的工具方法:一系列靜態(tài)方法實(shí)現(xiàn)對(duì)各種集合的搜索、排序旷余、線程安全化等操作
Collections常用方法:
- sort(Collection)方法的使用(含義:對(duì)集合進(jìn)行排序)绢记。
- binarySearch(Collection,Object)方法的使用(含義:查找指定集合中的元素,返回所查找元素的索引)正卧。
- max(Collection),max(Collection,Comparator)方法的使用(前者采用Collection內(nèi)含自然比較法蠢熄,后者采用Comparator進(jìn)行比較)。
- min(Collection),min(Collection,Comparator)方法的使用(前者采用Collection內(nèi)含自然比較法炉旷,后者采用Comparator進(jìn)行比較)签孔。
- indexOfSubList(List list,List subList)方法的使用(含義:查找subList在list中首次出現(xiàn)位置的索引)叉讥。
- lastIndexOfSubList(List source,List target)方法的使用(含義:查找target在list中最后出現(xiàn)位置的索引)。
- reverse()方法的使用(含義:反轉(zhuǎn)集合中元素的順序)饥追。
- rotate(List list,int m)方法的使用(含義:集合中的元素向后移m個(gè)位置图仓,在后面被遮蓋的元素循環(huán)到前面來)。
感興趣可以來這里看些小demo:
4. try catch finally但绕,try里有return救崔,finally還執(zhí)行么?
這個(gè)說實(shí)話真的看基本功了捏顺,相信平時(shí)工作認(rèn)真的小伙伴應(yīng)該也答得出來六孵,這里我貼上代碼。細(xì)節(jié)決定成敗你們贊同嗎幅骄?
try {
System.out.println("try");
return;
} catch (Exception e) {
System.out.println("catch");
}finally{
System.out.println("finally");
}
想必驗(yàn)證這個(gè)問題是個(gè)很簡(jiǎn)單的問題劫窒,但你剛剛認(rèn)為對(duì)了嗎?
*ps: *只有在try里面調(diào)用System.exit(0)來退出JVM的情況下finally塊中的代碼才不會(huì)執(zhí)行昌执。
5. Excption與Error包結(jié)構(gòu)烛亦。OOM你遇到過哪些情況诈泼,SOF你遇到過哪些情況懂拾。
Exception
(1) 可以是可被控制(checked) 或不可控制的(unchecked)。
(2) 表示一個(gè)由程序員導(dǎo)致的錯(cuò)誤铐达。
(3) 應(yīng)該在應(yīng)用程序級(jí)被處理岖赋。
Error
(1) 總是不可控制的(unchecked)。
(2) 經(jīng)常用來用于表示系統(tǒng)錯(cuò)誤或低層資源的錯(cuò)誤瓮孙。
(3) 如何可能的話唐断,應(yīng)該在系統(tǒng)級(jí)被捕捉
出現(xiàn)OOM的場(chǎng)景:
- 加載對(duì)象過大
- 相應(yīng)資源過多,來不及加載杭抠。
解決方案:
- 內(nèi)存引用上做一些處理脸甘,常用的有軟引用。
- 內(nèi)存中加載圖片直接在內(nèi)存中做處理(如邊界壓縮)這個(gè)Glide\Fresco 圖片框架可能封裝好了
- 優(yōu)化Delivk虛擬機(jī)的堆內(nèi)存分配偏灿、自定義堆內(nèi)存大小
- 合適的場(chǎng)景動(dòng)態(tài)回收內(nèi)存
SOF
程序中一旦出現(xiàn)死循環(huán)或者是大量的遞歸調(diào)用丹诀,在不斷的壓棧過程中,造成棧容量超過默認(rèn)大小而導(dǎo)致溢出翁垂。
棧溢出的原因:
- 遞歸調(diào)用
- 大量循環(huán)或死循環(huán)
- 全局變量是否過多
- 數(shù)組铆遭、List、map數(shù)據(jù)過
總結(jié):Error 表示系統(tǒng)級(jí)的錯(cuò)誤和程序不必處理的異常沿猜,是一種很嚴(yán)重的問題無法通過程序修復(fù)枚荣,比如內(nèi)存溢出,不可能指望程序能處理這樣的情況啼肩; Exception 表示需要捕捉或者需要程序進(jìn)行處理的異常橄妆,是一種設(shè)計(jì)或?qū)崿F(xiàn)問題衙伶,它表示如果程序運(yùn)行正常從不會(huì)發(fā)生的情況。而OOM和SOF大都是由于編碼不當(dāng)造成的程序內(nèi)存占用過高導(dǎo)致的問題害碾,所以為了避免程序少出問題養(yǎng)成一個(gè)好的編程習(xí)慣是很重要的這個(gè)就需要大家多多總結(jié)和實(shí)踐了痕支。
感興趣的小伙伴可以來這里看看:https://developer.android.com/topic/performance/memory.html
6. Java面向?qū)ο蟮娜齻€(gè)特征與含義。
封裝蛮原、繼承卧须、多態(tài)
封裝:通常認(rèn)為封裝是把數(shù)據(jù)和操作數(shù)據(jù)的方法綁定起來,對(duì)數(shù)據(jù)的訪問只能通過已經(jīng)定義的接口儒陨。面向?qū)ο蟮谋举|(zhì)就是將現(xiàn)實(shí)世界描繪成一系列完全自治花嘶、封閉的對(duì)象。我們?cè)陬愔芯帉懙姆椒ň褪菍?duì)實(shí)現(xiàn)細(xì)節(jié)的一種封裝蹦漠;我們編寫一個(gè)類就是對(duì)數(shù)據(jù)和數(shù)據(jù)操作的封裝椭员。可以說笛园,封裝就是隱藏一切可隱藏的東西隘击,只向外界提供最簡(jiǎn)單的編程接口。
繼承:
繼承是子對(duì)象繼承父對(duì)象的屬性和行為,亦即父對(duì)象擁有的屬性和行為宪萄,其子對(duì)象也就擁有了這些屬性和行為琼锋。這非常類似大自然中的物種遺傳(孩子跟父親是很像的,且也可以有自己的獨(dú)立行為)凶赁。
多態(tài):
多態(tài)是同一個(gè)行為具有多個(gè)不同表現(xiàn)形式或形態(tài)的能力,代碼中就是同一個(gè)接口使用不同的實(shí)例而執(zhí)行不同操作逆甜。
一張圖看明白多態(tài):
ps:打印機(jī)根據(jù)產(chǎn)物可以分為彩色和黑色打印機(jī)虱肄。他們都具有打印的作用,但是產(chǎn)物類似卻不同交煞。彩色打印機(jī)打印效果:彩色咏窿;黑白打印機(jī)打印效果:黑白色;其實(shí)這就是多態(tài)素征。
7. Override和Overload的含義及區(qū)別集嵌。
Overload 是重載的意思,Override 是覆蓋的意思稚茅,也就是重寫纸淮。
Overload(重載) 表示同一個(gè)類中可以有多個(gè)名稱相同的方法,但這些方法的參數(shù)列表各不相同(即參數(shù)個(gè)數(shù)亚享、類型或順序不同)咽块。
Override(重寫) 表示子類中的方法可以與父類中的某個(gè)方法的名稱和參數(shù)完全相同,通過子類創(chuàng)建的實(shí)例對(duì)象調(diào)用這個(gè)方法時(shí)欺税,將調(diào)用子類中的定義方法侈沪,這相當(dāng)于把父類中定義的那個(gè)完全相同的方法給覆蓋了揭璃,這也是面向?qū)ο缶幊痰亩鄳B(tài)性的一種表現(xiàn)。(ps:子類覆蓋父類的方法時(shí)亭罪,只能比父類拋出更少的異常瘦馍,或者是拋出父類拋出的異常的子異常,因?yàn)樽宇惪梢越鉀Q父類的一些問題应役,不能比父類有更多的問題情组。子類方法的訪問權(quán)限只能比父類的更大,不能更小箩祥。如果父類的方法 是 private 類型院崇,那么,子類則不存在覆蓋的限制袍祖,相當(dāng)于子類中增加了一個(gè)全新的方法底瓣。)
8. interface與abstract類的區(qū)別。
簡(jiǎn)單來說蕉陋,接口(interface)是公開的捐凭,里面不能有私有的方法或變量,是用于讓別人使用的凳鬓,而抽象類是可以有私有方法或私有變量的茁肠,另外,實(shí)現(xiàn)接口一定要實(shí)現(xiàn)接口里定義的所有方法村视,而實(shí)現(xiàn)抽象類(abstract)可以有選擇地重寫需要用到的方法官套。一般的應(yīng)用里,最頂級(jí)的是接口蚁孔,然后是抽象類實(shí)現(xiàn)接口,最后才到具體類實(shí)現(xiàn)惋嚎。
9. static class 與non static class的區(qū)別杠氢。
static class
- 靜態(tài)內(nèi)部類不需要有指向外部類的引用;
- 靜態(tài)類只能訪問外部類的靜態(tài)成員另伍,不能訪問外部類的非靜態(tài)成員鼻百;
non static class
- 非靜態(tài)內(nèi)部類需要持有對(duì)外部類的引用;
- 非靜態(tài)內(nèi)部類能夠訪問外部類的靜態(tài)和非靜態(tài)成員摆尝;
- 一個(gè)非靜態(tài)內(nèi)部類不能脫離外部類實(shí)體被創(chuàng)建温艇;
- 一個(gè)非靜態(tài)內(nèi)部類可以訪問外部類的數(shù)據(jù)和方法;
10. java多態(tài)的實(shí)現(xiàn)原理堕汞。
上面“6. Java面向?qū)ο蟮娜齻€(gè)特征與含義”已經(jīng)進(jìn)行多態(tài)的解釋勺爱。實(shí)現(xiàn)原理大致是:程序在運(yùn)行期間編譯器會(huì)去查找函數(shù)所對(duì)應(yīng)的具體對(duì)象,不同的對(duì)象相同的函數(shù)可以運(yùn)行出不同的結(jié)果讯检。(ps:我與小伙伴共同進(jìn)步琐鲁,哪里有問題或者您覺得自己的理解更全面歡迎拍磚留下腳游篮怠!)
未完待續(xù)~~~
喜歡有幫助的話围段、雙擊顾翼、評(píng)論、轉(zhuǎn)發(fā)奈泪,動(dòng)一動(dòng)你的小手讓更多的人知道适贸!關(guān)注 帥比-楊