愿你被這個(gè)世界溫柔以待
自天子以至于庶人,壹是皆以修身為本《禮記·大學(xué)》
馬老師說過,員工的離職原因很多炕柔,只有兩點(diǎn)最真實(shí):
錢酌泰,沒給到位
心,受委屈了
當(dāng)然匕累,我是想換個(gè)平臺(tái)陵刹,換個(gè)方向,想清楚為什么要跳槽欢嘿,如果真的要跳槽衰琐,想要拿到一個(gè)理想的offer,除了運(yùn)氣炼蹦,基本功也要足夠的扎實(shí)羡宙,希望下面的面試經(jīng)驗(yàn)?zāi)芙o你們能夠提供一些幫助。
項(xiàng)目經(jīng)驗(yàn)
面試官在一開始會(huì)讓你進(jìn)行自我介紹掐隐,主要是想讓你介紹一下自己做過的一些項(xiàng)目辛辨,看看你對(duì)這些項(xiàng)目的了解程度,因?yàn)楹芏嗳撕?jiǎn)歷上寫的項(xiàng)目并非都是從頭到尾都參與的瑟枫,有些只是參與并實(shí)現(xiàn)了其中的一些模塊而已斗搞,或是接手維護(hù)別人的項(xiàng)目,所以在你簡(jiǎn)歷上所寫的和面試過程中所說的項(xiàng)目經(jīng)驗(yàn)慷妙,你自己必須能夠了解來龍去脈僻焚,因?yàn)槊嬖嚬倏隙〞?huì)根據(jù)你的項(xiàng)目描述,對(duì)項(xiàng)目中的實(shí)現(xiàn)原理膝擂,或?yàn)槭裁匆@樣實(shí)現(xiàn)進(jìn)行提問虑啤,這時(shí)不至于木訥住而不知如何作答,如此局面只會(huì)大大降低面試分架馋。
場(chǎng)景對(duì)話:
面試官:(拿著簡(jiǎn)歷)講講你最近做的這個(gè)項(xiàng)目
我:&……%¥#*&¥@%¥狞山!,說了一大通(不知道面試官聽進(jìn)去多少叉寂,面試官會(huì)挑他會(huì)的進(jìn)行提問)
面試官:你說這個(gè)項(xiàng)目中用到了netty萍启,能大概講講netty的線程模型么?
我:(幸好我看過netty的源碼)netty通過Reactor模型基于多路復(fù)用器接收并處理用戶請(qǐng)求(能講就多講一點(diǎn))屏鳍,內(nèi)部實(shí)現(xiàn)了兩個(gè)線程池勘纯,boss線程池和work線程池,其中boss線程池的線程負(fù)責(zé)處理請(qǐng)求的accept事件钓瞭,當(dāng)接收到accept事件的請(qǐng)求時(shí)驳遵,把對(duì)應(yīng)的socket封裝到一個(gè)NioSocketChannel中,并交給work線程池山涡,其中work線程池負(fù)責(zé)請(qǐng)求的read和write事件(通過口述加畫圖的方式堤结,把請(qǐng)求的執(zhí)行過程大概描述了一遍唆迁,時(shí)間有限,也不可能把所有的細(xì)節(jié)都說完竞穷,挑重點(diǎn)講唐责,挑記憶深刻的講)
面試官:嗯,理解的還挺深入的...那你在做這個(gè)項(xiàng)目時(shí)有沒有遇到什么困難来庭,或者是覺得有挑戰(zhàn)的地方?
我:(這時(shí)面試官想讓你自己出題自己回答了穿挨,所以一定要回答月弛,不回答就突顯不出你這個(gè)項(xiàng)目了,要是這個(gè)問題沒有準(zhǔn)備過科盛,只能臨時(shí)發(fā)揮了帽衙,當(dāng)然我就是屬于臨時(shí)發(fā)揮的)稍微想一下,因?yàn)橹按_實(shí)碰到了這個(gè)問題贞绵,當(dāng)時(shí)做這個(gè)項(xiàng)目時(shí)厉萝,對(duì)netty的不過熟悉,把請(qǐng)求的業(yè)務(wù)邏輯放在work線程池的線程中進(jìn)行處理榨崩,進(jìn)行壓測(cè)的時(shí)候谴垫,發(fā)現(xiàn)qps總是上不去,后來看了源碼之后才發(fā)現(xiàn)母蛛,由于業(yè)務(wù)邏輯的處理比較耗時(shí)翩剪,完全占用了work線程池的資源,導(dǎo)致新的請(qǐng)求一直處于等待狀態(tài)彩郊。
面試官:那最后是如何解決的前弯?
我:最后把處理業(yè)務(wù)的邏輯封裝成一個(gè)task提交給一個(gè)新建的業(yè)務(wù)線程池中執(zhí)行,執(zhí)行完之后由work線程池執(zhí)行請(qǐng)求的write事件秫逝。
面試官:好的恕出,你知道nio中selector可能觸發(fā)bug么?
我:嗯违帆,對(duì)的浙巫,selector的select方法,因?yàn)榈讓拥膃poll函數(shù)可能會(huì)發(fā)生空轉(zhuǎn)刷后,從而導(dǎo)致cpu100%狈醉。
面試官:那如何解決該問題?
我:這個(gè)問題在netty已經(jīng)解決了惠险,通過&%&$(把netty的解決方案說一遍)
面試官:嗯苗傅,對(duì)了,你們這個(gè)項(xiàng)目有給自己定指標(biāo)么班巩?
我:有的渣慕,&&…………¥¥##@嘶炭,把自己項(xiàng)目的指標(biāo)說了一通,如何進(jìn)行AB實(shí)驗(yàn)逊桦,如何迭代優(yōu)化指標(biāo)
面試官:嗯眨猎,好的 ,項(xiàng)目的問題先到這里强经,我們來考察一下java的基本點(diǎn)吧睡陪。
如上只是本人所做的一個(gè)項(xiàng)目,當(dāng)然了匿情,具體項(xiàng)目具體分析兰迫,也不是每個(gè)面試官問的點(diǎn)都一樣,如果面試官不懂netty炬称,自然會(huì)挑別的問題進(jìn)行提問汁果,不過你也可以嘗試著把問題往自己熟悉的方向去靠。
面試知識(shí)點(diǎn)
1玲躯、線程池
線程池的實(shí)現(xiàn)原理据德,這個(gè)知識(shí)點(diǎn)真的很重要,幾乎每次面試都會(huì)被問到跷车,一般的提問方式有如下幾種:
1棘利、“講講線程池的實(shí)現(xiàn)原理”
2、“線程池中的coreNum和maxNum有什么不同”
3朽缴、“在不同的業(yè)務(wù)場(chǎng)景中赡译,線程池參數(shù)如何設(shè)置”
場(chǎng)景對(duì)話:
面試官:平時(shí)線程池用的多么?
我:嗯不铆,我的***項(xiàng)目中就用到了
面試官:那好蝌焚,你講講線程池的實(shí)現(xiàn)原理
我:(還好我之前看過源碼,但是時(shí)間久遠(yuǎn)有點(diǎn)模糊了)誓斥,能給我筆和紙么只洒,我畫圖分析給你看看,&&¥&假設(shè)初始化一個(gè)線程池劳坑,核心線程數(shù)是5毕谴,最大線程數(shù)是10@@@
面試官:嗯,好的距芬,你繼續(xù)...
我:在紙上畫了正方形涝开,這個(gè)代表一個(gè)線程池,初始化的時(shí)候框仔,里面是沒有線程的
面試官:嗯舀武,好的,你繼續(xù)...
我:又畫了一個(gè)細(xì)長(zhǎng)的長(zhǎng)方形离斩,這個(gè)代表阻塞隊(duì)列银舱,一開始里面也是沒有任務(wù)的
面試官:嗯瘪匿,好的,你繼續(xù)...
我:當(dāng)來了一個(gè)任務(wù)時(shí)寻馏,在正方形中畫了一個(gè)小圓圈棋弥,代表初始化了一個(gè)線程,如果再來一個(gè)任務(wù)诚欠,就再畫一個(gè)圓圈顽染,表示再初始化了一個(gè)線程,連續(xù)畫了5個(gè)圓圈之后轰绵,如果第6個(gè)任務(wù)過來了...
面試官:嗯粉寞,好的,你繼續(xù)...
我:這時(shí)會(huì)把第6個(gè)任務(wù)放到阻塞隊(duì)列中..
面試官:嗯藏澳,然后呢仁锯?
我:現(xiàn)在線程池中不是有5個(gè)線程了么耀找,如果其中一個(gè)線程空閑了翔悠,就會(huì)從阻塞隊(duì)列中獲取第6個(gè)任務(wù),進(jìn)行執(zhí)行..
面試官:嗯野芒,對(duì)的蓄愁,那如果任務(wù)產(chǎn)生的速度比消費(fèi)的速度快呢?
我:如果線程池的5個(gè)線程都在running狀態(tài)狞悲,那么任務(wù)就先保存在阻塞隊(duì)列中
面試官:如果隊(duì)列滿了撮抓,怎么辦?
我:如果隊(duì)列滿了摇锋,我們不是設(shè)置了最大線程數(shù)是10么丹拯,而線程池中只有5個(gè)線程,這時(shí)會(huì)新建一個(gè)線程去執(zhí)行不能保存到阻塞隊(duì)列的任務(wù)荸恕,然后我又在正方形中畫了5個(gè)圓圈乖酬。
面試官:那如果線程池中的線程數(shù)達(dá)到10個(gè)了,阻塞隊(duì)列也滿了融求,怎么辦咬像?
我:這種情況通過自定義reject函數(shù)去處理這里任務(wù)了,舒了一口去生宛,以為問完了...
面試官:好的县昂,那如果運(yùn)行一段時(shí)間之后,阻塞隊(duì)列中的任務(wù)也執(zhí)行完了陷舅,線程池中的線程會(huì)怎么樣倒彰?
我:...這個(gè)好像超過核心線程數(shù)的線程會(huì)在空閑一段時(shí)間內(nèi)自動(dòng)回收...因?yàn)橛悬c(diǎn)不記得這個(gè)邏輯了,回答的有點(diǎn)虛...
面試官:好的莱睁,那這種情況在什么場(chǎng)景下會(huì)發(fā)生?
我:(有時(shí)候真是笨啊狸驳,很多東西都知道预明,但是在面試的時(shí)候一緊張,全忘記)這個(gè)...那個(gè)...我好像沒有遇到過這樣的情況
面試官:嗯耙箍,好的撰糠,你回去之后再好好想想
我:........
2、鎖的實(shí)現(xiàn)
在關(guān)于鎖的面試過程中辩昆,一般主要問Synchronized和ReentrantLock的實(shí)現(xiàn)原理阅酪,更有甚者會(huì)問讀寫鎖。
場(chǎng)景對(duì)話:
面試官:都了解Java中的什么鎖汁针?
我:比如Synchronized和ReentrantLock...讀寫鎖用的不多术辐,就沒研究了(我就怕被問讀寫鎖,因?yàn)橐恢睕]去看)
面試官:那好施无,你先說說Synchronized的實(shí)現(xiàn)原理吧
我:嗯辉词,Synchronized是JVM實(shí)現(xiàn)的一種鎖,其中鎖的獲取和釋放分別是monitorenter和monitorexit指令猾骡,該鎖在實(shí)現(xiàn)上分為了偏向鎖瑞躺、輕量級(jí)鎖和重量級(jí)鎖,其中偏向鎖在1.6是默認(rèn)開啟的兴想,輕量級(jí)鎖在多線程競(jìng)爭(zhēng)的情況下會(huì)膨脹成重量級(jí)鎖幢哨,有關(guān)鎖的數(shù)據(jù)都保存在對(duì)象頭中...&&@@#,(嗯嫂便,說了一大堆捞镰,面試官也沒打斷我)
面試官:哦,嗯毙替,理解的還挺透徹岸售,那你說說ReentrantLock的實(shí)現(xiàn)吧...
我:ReentrantLock是基于AQS實(shí)現(xiàn)的
面試官:什么是AQS?
我:在AQS內(nèi)部會(huì)保存一個(gè)狀態(tài)變量state厂画,通過CAS修改該變量的值凸丸,修改成功的線程表示獲取到該鎖,沒有修改成功木羹,或者發(fā)現(xiàn)狀態(tài)state已經(jīng)是加鎖狀態(tài)甲雅,則通過一個(gè)Waiter對(duì)象封裝線程,添加到等待隊(duì)列中坑填,并掛起等待被喚醒&&&$$(又說了一堆)
面試官:能說說CAS的實(shí)現(xiàn)原理么抛人?
我:CAS是通過unsafe類的compareAndSwap方法實(shí)現(xiàn)的(心里得意的一笑)
面試官:哦,好的脐瑰,那你知道這個(gè)方法的參數(shù)的含義的么妖枚?
我:(這是在逼我啊...努力的回想,因?yàn)槲艺娴目催^安栽凇)我想想啊绝页,這個(gè)方法看的時(shí)間有點(diǎn)久遠(yuǎn)了荠商,第一個(gè)參數(shù)是要修改的對(duì)象,第二個(gè)參數(shù)是對(duì)象中要修改變量的偏移量续誉,第三個(gè)參數(shù)是修改之前的值莱没,第四個(gè)參數(shù)是預(yù)想修改后的值....(說出來之后都有點(diǎn)佩服自己,這個(gè)都記得酷鸦,不過面試官好像還是不肯放過我...)
面試官:嗯饰躲,對(duì)的,那你知道操作系統(tǒng)級(jí)別是如何實(shí)現(xiàn)的么臼隔?
我:(我去你大爺...)我只記得X86中有一個(gè)cmp開頭的指令嘹裂,具體的我忘記了...
面試官:嗯,好摔握,你知道CAS指令有什么缺點(diǎn)么
我:哦寄狼,CAS的缺點(diǎn)是存在ABA問題
面試官:怎么講?
我:就是一個(gè)變量V氨淌,如果變量V初次讀取的時(shí)候是A泊愧,并且在準(zhǔn)備賦值的時(shí)候檢查到它仍然是A,那能說明它的值沒有被其他線程修改過了嗎宁舰?如果在這段期間它的值曾經(jīng)被改成了B拼卵,然后又改回A奢浑,那CAS操作就會(huì)誤認(rèn)為它從來沒有被修改過蛮艰。
面試官:那怎么解決?
我:(有完沒完了啊...我的心里是崩潰的)針對(duì)這種情況雀彼,java并發(fā)包中提供了一個(gè)帶有標(biāo)記的原子引用類"AtomicStampedReference"壤蚜,它可以通過控制變量值的版本來保證CAS的正確性。
面試官:嗯徊哑,好的袜刷,這個(gè)問題到此為止,我們?cè)倏纯磩e的
我:....我能喝口水么
3莺丑、ConcurrentHashMap
當(dāng)考察數(shù)據(jù)結(jié)構(gòu)時(shí)著蟹,面試官一開始會(huì)問HashMap的實(shí)現(xiàn)原理,當(dāng)你說出HashMap并非線程安全之后梢莽,會(huì)讓你自己引出ConcurrentHashMap萧豆,接著就可能開始如下的對(duì)話。
場(chǎng)景對(duì)話:
面試官:談?wù)凜oncurrentHashMap實(shí)現(xiàn)原理
我:@#¥@@基于分段鎖的%%¥#@#¥昏名,但是1.8之后改變實(shí)現(xiàn)方式了
面試官:1.8啥方式
我:把1.8的實(shí)現(xiàn)原理說了一通涮雷,其中提到了紅黑樹...
面試官:能講下紅黑樹的概念嗎
我:紅黑樹是一種二叉樹,并且是平衡……%……¥……轻局,
面試官:能講下紅黑樹的洪鸭。样刷。。览爵。置鼻。
我:打住,別問了蜓竹,紅黑樹我只知道他是二叉樹沃疮,比其他樹多一個(gè)屬性,其他的我都不知道
面試官:好的梅肤,那換個(gè)司蔬,你知道它的size方法是如何實(shí)現(xiàn)的么?
我:size方法姨蝴?是想要得到Map中的元素個(gè)數(shù)么俊啼?
面試官:對(duì)的....
我:我記得好像size方法返回是不準(zhǔn)確的,平時(shí)也不會(huì)用到這個(gè)方法...
面試官:如果你覺得size方法返回值不準(zhǔn)確左医,那如果讓你自己實(shí)現(xiàn)授帕,你覺得應(yīng)該怎么實(shí)現(xiàn)呢?
我:...@#¥@@...兩眼一黑
我:等等浮梢,讓我想想.....應(yīng)該可以用AtomicInteger變量進(jìn)行記錄...嗯跛十,對(duì)的,每次插入或刪除的時(shí)候秕硝,操作這個(gè)變量芥映,我得意的一笑...
面試官:哦,是么远豺,那如果我覺得這個(gè)AtomicInteger這個(gè)變量性能不好奈偏,還能再優(yōu)化么?
我:懵逼臉...(當(dāng)時(shí)居然把volitile變量給忘記了)...好像沒有了躯护,我想不出來了...
面試官:哦惊来,那回頭你再看看源碼吧,jdk中已經(jīng)實(shí)現(xiàn)了...
我:哦棺滞,是么....
面試官:那今天的面試到此結(jié)束裁蚁,我們后面會(huì)通知你。
我:..................
在此我向大家推薦一個(gè)架構(gòu)學(xué)習(xí)交流群继准。交流學(xué)習(xí)群號(hào):874811168 ?里面會(huì)分享一些資深架構(gòu)師錄制的視頻錄像:有Spring枉证,MyBatis,Netty源碼分析锰瘸,高并發(fā)刽严、高性能、分布式、微服務(wù)架構(gòu)的原理舞萄,JVM性能優(yōu)化眨补、分布式架構(gòu)等這些成為架構(gòu)師必備的知識(shí)體系。還能領(lǐng)取免費(fèi)的學(xué)習(xí)資源倒脓,目前受益良多
原文出處:http://www.reibang.com/p/1b2f63a45476