學習筆記面試寶典_第1頁
學習筆記面試寶典_第2頁
學習筆記面試寶典_第3頁
學習筆記面試寶典_第4頁
已閱讀5頁,還剩7頁未讀 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)

文檔簡介

1、基礎(chǔ)篇1、TCP、UDP的區(qū)別?TCP與UDP區(qū)別總結(jié):1. TCP面向連接(如打 要先撥號建立連接);UDP是無連接的,即 數(shù)據(jù)之前不需要建立連接。2. TCP提供可靠的服務(wù)。也就是說,通過TCP連接傳送的數(shù)據(jù),無差錯,不丟失,不重復,且按序到 達;UDP盡最大努力交付,即不保證可靠交付3. TCP面向字節(jié)流,實際上是TCP把數(shù)據(jù)看成一連串無結(jié)構(gòu)的字節(jié)流;UDP是面向報文的 UDP沒有擁塞 ,因此網(wǎng)絡(luò)出現(xiàn)擁塞 使源主機的 速率降低(對實時應(yīng)用很有用,如IP ,實時視頻會議等)4. 每一條TCP連接只能是點到點的;UDP支持一對一,一對多,多對一和多對多的交互通信5. TCP首部開銷20字節(jié);

2、UDP的首部開銷小,只有8個字節(jié)6. TCP的邏輯通信信道是全雙工的可靠信道,UDP則是不可靠信道2、TCP協(xié)議如何保證可靠傳輸?校驗和,確認 和序列號序列號:TCP傳輸時將每個字節(jié)的數(shù)據(jù)都進行了編號,這就是序列號。確認 :TCP傳輸?shù)倪^程中,每次接收方收到數(shù)據(jù)后,都會對傳輸方進行確認 。也就是 ACK報文。這個ACK報文當中帶有對應(yīng)的確認序列號,告訴 方,接收到了哪些數(shù)據(jù),下一次的數(shù)據(jù)從哪里發(fā)。序列號的作用不僅僅是 的作用,有了序列號能夠?qū)⒔邮盏降臄?shù)據(jù)根據(jù)序列號排序,并且去掉重復序列號的數(shù)據(jù)。這也是TCP傳輸可靠性的保證之一。超時重傳:當TCP發(fā)出一個 ,它啟動一個定時器,等待目的端確認收到

3、這個報文段。如果不 收到一個確認,將重發(fā)這個報文段。流量 :TCP連接的每一方都有固定大小的緩沖空間,TCP的接收端只 端 接收端緩沖區(qū)能接納的數(shù)據(jù)。當接收方來不及處理 方的數(shù)據(jù),能提示 方降低 的速率,防止包丟失。TCP使用的流量 協(xié)議是可變大小的滑動窗口協(xié)議。接收方有即時窗口(滑動窗口),隨ACK報文發(fā)送擁塞 :如果網(wǎng)絡(luò)出現(xiàn)擁塞,分組將會丟失,此時 方會繼續(xù)重傳,從而導致網(wǎng)絡(luò)擁塞程度更高。因此當出現(xiàn)擁塞時,應(yīng)當這一點和流量 很像,但是出發(fā)點不同。流量 是 接收方能來得及接收,而擁塞 是為了降低整個網(wǎng)絡(luò)的擁塞程度。TCP 主要通過四個算法來進行擁塞 :慢開始、擁塞避免、快重傳、快恢復。3、T

4、CP的握手、揮 制?TCP的握 制:TCP的揮 制:詳情參考:4、TCP的粘包/拆包 及其解決方法是什么?為什么會發(fā)生TCP粘包、拆包? 發(fā)生TCP粘包、拆包主要是由于下面一些 :1. 應(yīng)用程序?qū)懭氲臄?shù)據(jù)大于套接字緩沖區(qū)大小,這將會發(fā)生拆包。2. 應(yīng)用程序?qū)懭霐?shù)據(jù)小于套接字緩沖區(qū)大小,網(wǎng)卡將應(yīng)用多次寫入的數(shù)據(jù) 到網(wǎng)絡(luò)上,這將會發(fā)生粘包。3. 進行MSS(最大報文長度)大小的TCP分段,當TCP報文長度-TCP頭部長度MSS的時候?qū)l(fā)生拆 包。4. 接收方法不及時 套接字緩沖區(qū)數(shù)據(jù),這將發(fā)生粘包。粘包、拆包解決辦法:TCP本身是面向流的,作為網(wǎng)絡(luò)服務(wù)器,如何從這源源不斷涌來的數(shù)據(jù)流中拆分出或者合

5、并出有意義的信息呢?通常會有以下一些常用的方法:1. 端給每個數(shù)據(jù)包添加包首部,首部中應(yīng)該至少包含數(shù)據(jù)包的長度,這樣接收端在接收到數(shù)據(jù)后,通過 包首部的長度字段,便知道每一個數(shù)據(jù)包的實際長度了。2. 端將每個數(shù)據(jù)包封裝為固定長度(不夠的可以通過補0填充),這樣接收端每次從接收緩沖區(qū)中 固定長度的數(shù)據(jù)就自然而然的把每個數(shù)據(jù)包拆 來。3. 可以在數(shù)據(jù)包之間設(shè)置邊界,如添加特殊符號,這樣,接收端通過這個邊界就可以將不同的數(shù)據(jù)包拆 。5、Netty的粘包/拆包是怎么處理的,有哪些實現(xiàn)?對于粘包和拆包問題,常見的解決方案有四種:1. 客戶端在 數(shù)據(jù)包的時候,每個包都固定長度,比如1024個字節(jié)大小,如果

6、客戶端 的數(shù)據(jù)長度不足1024個字節(jié),則通過補充空格的方式補全到指定長度;Netty提供的FixedLengthFrameDecoder2. 客戶端在每個包的末尾使用固定的分隔符,例如rn,如果一個包被拆分了,則等待下一個包過來之后找到其中的rn,然后對其拆分后的頭部部分與前一個包的剩余部分進行合并,這樣就得到了一個完整的包;Netty提供LineBasedFrameDecoder與DelimiterBasedFrameDecoder3. 將消息分為頭部和消息體,在頭部中保存有當前整個消息的長度,只有在 到足夠長度的消息之后才算是讀到了一個完整的消息;Netyy提供了LengthFieldBa

7、sedFrameDecoder與LengthFieldPrepender4. 通過自定義協(xié)議進行粘包和拆包的處理。Netty提供了通過實現(xiàn)MessageToByteEncoder和ByteToMessageDecoder來實現(xiàn)6、同步與異步、阻塞與非阻塞的區(qū)別?簡單點理解就是:1. 同步,就是我調(diào)用一個功能,該功能沒有結(jié)束前,我死等結(jié)果。2. 異步,就是我調(diào)用一個功能,不需要知道該功能結(jié)果,該功能有結(jié)果后通知我(回調(diào)通知)3. 阻塞,就是調(diào)用我(函數(shù)),我(函數(shù))沒有接收完數(shù)據(jù)或者沒有得到結(jié)果之前,我 返回。4. 非阻塞,就是調(diào)用我(函數(shù)),我(函數(shù))立即返回,通過select通知調(diào)用者同步I

8、O和異步IO的區(qū)別就在于:數(shù)據(jù)拷貝的時候進程是否阻塞 阻塞IO和非阻塞IO的區(qū)別就在于:應(yīng)用程序的調(diào)用是否立即返回7、說說網(wǎng)絡(luò)IO模型?8、BIO、NIO、AIO分別是什么?BIO:同步并阻塞 ,服務(wù)器實現(xiàn)模式為 接一個線程,即客戶端有連接請求時服務(wù)器端就需要啟動 一個線程進行處理,如果這個連接不做任何事情會造成不必要的線程開銷,當然可以通過線程池機制改 善。BIO方式適用于連接數(shù)目比較小且固定的架構(gòu),這種方式對服務(wù)器 要求比較高,并發(fā)局限于應(yīng)用中,JDK1.4以前的唯一選擇,但程序直觀簡單易理解。NIO:同步非阻塞 ,服務(wù)器實現(xiàn)模式為一個請求一個線程,即客戶端 的連接請求都會 到多路復用器上

9、,多路復用器輪詢到連接有I/O請求 啟動一個線程進行處理。NIO方式適用于連接數(shù)目多且連接比較短(輕操作)的架構(gòu),比如聊天服務(wù)器,并發(fā)局限于應(yīng)用中,編程比較復雜,JDK1.4開始支持。AIO:異步非阻塞 ,服務(wù)器實現(xiàn)模式為一個有效請求一個線程,客戶端的I/O請求都是由OS先完成了再通知服務(wù)器應(yīng)用去啟動線程進行處理.AIO方式使用于連接數(shù)目多且連接比較長(重操作)的架構(gòu),比如相 冊服務(wù)器,充分調(diào)用OS參與并發(fā)操作,編程比較復雜,JDK7開始支持。9、select、poll、epoll的機制及其區(qū)別?單個進程打開的文件描述符(fd文件句柄)不一致select :有最大連接數(shù)限制數(shù)為1024,單個進

10、程所能打開的最大連接數(shù)由FD_ZETSIZE宏定義。poll:poll本質(zhì)上與select沒有區(qū)別,但是它沒有最大連接數(shù)的限制, 是它是基于鏈表來的。epoll:雖然連接有上限,但是很大,1G內(nèi)存的 可以打開10萬左右的連接,以此類推。Socket的方式不一致select :輪詢的方式,一個一個的socket檢查過去,發(fā)現(xiàn)有socket活躍 進行處理,當線性socket增多時,輪詢的速度將會變得很慢,造成線性造 能下降問題。poll:對select稍微進行了優(yōu)化,只是修改了文件描述符,但是 socket的方式還是輪詢。expoll:epoll內(nèi)核中實現(xiàn)是根據(jù)每個fd上的callback函數(shù)來實

11、現(xiàn)的,只有活躍的socket才會主動 調(diào)用callback,通知expoll來處理這個socket。(會將連接的socket 到epoll中, 相當于socket 的花名冊, 如果有一個socket活躍了, 會回調(diào)一個函數(shù), 通知epoll,趕緊過來處理)內(nèi)存空間拷貝方式(消息傳遞方式)不一致 select:內(nèi)核想將消息傳遞到用戶態(tài),需要將數(shù)據(jù)從內(nèi)核態(tài)拷貝到用戶態(tài),這個過程非常的耗時poll:同上epoll:epoll的內(nèi)核和用戶空間共享一塊內(nèi)存,因此內(nèi)存態(tài)數(shù)據(jù)和用戶態(tài)數(shù)據(jù)是共享的select、poll、epoll時間復雜度分別是:O(n)、O(n)、O(1)10、Netty跟Java NIO

12、有什么不同,為什么不直接使用JDK NIO類庫?NIO有什么缺點:NIO的類庫和API還是有點復雜,比如Buffer的使用 Selector編寫復雜,如果對某個 后,業(yè)務(wù)代碼過于耦合 需要了解很多多線程的知識,熟悉網(wǎng)絡(luò)編程 面對斷 連、保丟失、粘包等,處理復雜NIO存在BUG,根據(jù)網(wǎng)上 說是selector空輪訓導致CPU飆升,具體有 的 JDK的官網(wǎng)Netty主要的優(yōu)點有:框架設(shè)計優(yōu)雅,底層模型隨意切換適應(yīng)不同的網(wǎng)絡(luò)協(xié)議要求提供很多標準的協(xié)議、安全、編碼 的支持解決了很多NIO不易用的問題在很多開源框架中使用,如Dubbo、RocketMQ、Spark等底層 有:Zero-Copy-Capa

13、ble Buffer,非常易用的靈拷貝Buffer(這個內(nèi)容很有意思,稍后專門來說);統(tǒng)一的API; 擴展的時間模型傳輸方面的支持有:管道通信(具體不知道干啥的,還請老司機指教);Http隧道;TCP與UDP協(xié)議方面的支持有:基于原始文本和二進制的協(xié)議;解壓縮;大文件傳輸;流 傳輸;protobuf編 ;安全認證;http和websocket總之提供了很多現(xiàn)成的功能可以直接供開發(fā)者使用。12、Netty組件有哪些,分別有什么關(guān)聯(lián)?ChannelSocketEventLoop流,多線程處理,并發(fā);ChannelHandler和ChannelPipeline Bootstrap 和 ServerB

14、ootstrap13、說說Netty的執(zhí)行流程?1. 創(chuàng)建ServerBootStrap實例2. 設(shè)置并綁定Reactor線程池:EventLoopGroup,EventLoop就是處理所有 到本線程的Selector上面的Channel3. 設(shè)置并綁定服務(wù)端的channel4. 創(chuàng)建處理網(wǎng)絡(luò) 的ChannelPipeline和handler,網(wǎng)絡(luò)時間以流的形式在其中流轉(zhuǎn),handler完成 多數(shù)的功能定制:比如編 SSl安全認證5. 綁定并啟動 端口6. 當輪訓到準備就緒的channel后,由Reactor線程:NioEventLoop執(zhí)行pipline中的方法,最終調(diào)度 并執(zhí)行channe

15、lHandler高級篇14、Netty高性能體現(xiàn)在哪些方面?.15、Netty的線程模型是怎么樣的?Reactor線程模型Reactor單線程模型 一個NIO線程+一個accept線程:Reactor多線程模型Reactor主從模型 主從Reactor多線程:多個acceptor的NIO線程池用于接受客戶端的連接Netty可以基于如上三種模型進行靈活的配置??偨Y(jié)Netty是建立在NIO基礎(chǔ)之上,Netty在NIO之上又提供了更 次的抽象。在Netty里面,Accept連接可以使用單獨的線程 處理,讀寫操作又是另外的線程 處理。Accept連接和讀寫操作也可以使用同一個線程 進行處理。而請求處理

16、邏輯既可以使用單獨的線程 處理,也可以跟放在讀寫線程一塊處理。線程 的每一個線程都是NIO線程。用戶可以根據(jù)實際情況進行組裝,構(gòu)造出滿足系統(tǒng)需求的高性能并發(fā)模型。16、Netty的零拷貝提體現(xiàn)在哪里,與操 上的有什么區(qū)別?傳統(tǒng)意義的拷貝是在 數(shù)據(jù)的時候, 傳統(tǒng)的實現(xiàn)方式是:1. File.read(bytes)2. Socket.send(bytes)這種方式需要四次數(shù)據(jù)拷貝和四次上下文切換:1. 數(shù)據(jù)從磁盤 到內(nèi)核的read buffer2. 數(shù)據(jù)從內(nèi)核緩沖區(qū)拷貝到用戶緩沖區(qū)3. 數(shù)據(jù)從用戶緩沖區(qū)拷貝到內(nèi)核的socket buffer4. 數(shù)據(jù)從內(nèi)核的socket buffer拷貝到網(wǎng)卡接口

17、(硬件)的緩沖區(qū)零拷貝的概念明顯上面的第二 第三步是沒有必要的,通過java的FileChannel.transferTo方法,可以避免上面兩次多余的拷貝(當然這需要底層操 支持)1. 調(diào)用transferTo,數(shù)據(jù)從文件由DMA引擎拷貝到內(nèi)核read buffer2. 接著DMA從內(nèi)核read buffer將數(shù)據(jù)拷貝到網(wǎng)卡接口buffer上面的兩次操作都不需要CPU參與,所以就達到了零拷貝。Netty中的零拷貝主要體現(xiàn)在三個方面:1、bytebufferNetty 和接收消息主要使用bytebuffer,bytebuffer使用對外內(nèi)存(DirectMemory)直接進行Socket讀寫。

18、:如果使用傳統(tǒng)的堆內(nèi)存進行Socket讀寫,JVM會將堆內(nèi)存buffer拷貝一份到直接內(nèi)存中然后再寫入socket,多了一次緩沖區(qū)的內(nèi)存拷貝。DirectMemory中可以直接通過DMA 到網(wǎng)卡接口2、Composite Buffers傳統(tǒng)的ByteBuffer,如果需要將兩個ByteBuffer中的數(shù)據(jù)組合到一起,我們需要首先創(chuàng)建一個size=size1+size2大小的新的數(shù)組,然后將兩個數(shù)組中的數(shù)據(jù)拷貝到新的數(shù)組中。但是使用Netty提供的組合ByteBuf,就可以避免這樣的操作,因為CompositeByteBuf并沒有真正將多個 Buffer組合起來,而是保存了它們的 ,從而避免了數(shù)

19、據(jù)的拷貝,實現(xiàn)了零拷貝。3、對于FileChannel.transferTo的使用Netty中使用了FileChannel的transferTo方法,該方法依賴于操實現(xiàn)零拷貝。17、Netty的內(nèi)存 怎么實現(xiàn)的?netty內(nèi)存池實現(xiàn)原理netty內(nèi)存池可以分配堆內(nèi)存和 內(nèi)存(Direct內(nèi)存),內(nèi)存分配的 算法是類似的,從堆內(nèi)存分配代碼入手來學習整個內(nèi)存池的原理。netty框架處理IO 時,使用ByteBuf承載數(shù)據(jù)。ByteBuf的內(nèi)存分配由PooledByteBufAllocator來執(zhí)行,最終的內(nèi)存分配工作會被委托給PoolArena,堆內(nèi)存分配的PoolArena實現(xiàn)是HeapAren

20、ty通常被用于高并發(fā)系統(tǒng),多線程競爭加鎖會影響內(nèi)存分配的效率,為了緩解高并發(fā)時的線程競爭,netty 使用者創(chuàng)建多個分配器(PoolArena)來分離線程競爭,提高內(nèi)存分配效率??赏ㄟ^PooledByteBufAllocator構(gòu)造子中的nHeapArena參數(shù)來設(shè)置PoolArena的數(shù)量,或者直接取框架中的 默認值,通過以下代碼決定默認值,默認值根據(jù)CPU 數(shù)、JVM最大可用內(nèi)存以及默認內(nèi)存塊(PoolChunk)大小等參數(shù)來計算這個默認值,計算邏輯是:1)獲取系統(tǒng)變量ty.allocator.numHeapArenas,通過System.setProperty(ty.alloc

21、ator.numHeapArenas, )或者增加JVM啟動參數(shù)- Dty.allocator.numHeapArenas= 設(shè)置,如果設(shè)置了值,把這個值當做Arena的個數(shù)。2)如果沒有設(shè)置ty.allocator.numHeapArenas系統(tǒng)變量,計算CPU 數(shù)*2和JVM最大可用內(nèi)存/默認內(nèi)存塊大小/2/3,取其中一個較少的值當做PoolArena的個數(shù)。確定PoolArena個數(shù)之后框架會創(chuàng)建一個PoolArena數(shù)組,數(shù)組中所有的PoolArena都會用來執(zhí)行內(nèi)存 分配。線程申請內(nèi)存分配時,線程會在這個PoolArena數(shù)組中挑選一個當前被占用次數(shù)最少的Arena執(zhí)行內(nèi)存分配。此外

22、,netty使用擴展的線程對象FastThreadLocalThread來優(yōu)化ThreadLocal性能,具體的優(yōu)化思路 是:默認的ThreadLocal使用ThreadLocalMap 線程局部變量,它的實現(xiàn)方式類似于HashMap,需 要計算hashCode 到線程局部變量所在Entry的索引,而FastThreadLocalThread使用FastThreadLocal代替ThreadLocal,F(xiàn)astThreadLocalThread用一個數(shù)組來維護線程變量,每個FastThreadLocal維護一個index,該index就是線程局部變量在數(shù)組中的位置,線程變量直接通過index無需計算hashCode,F(xiàn)astThreadLocal的優(yōu)勢是減少了hashCode的計算過程,雖然性能只會有輕微的提升,但在高并發(fā)系統(tǒng)中,即使只是輕微的提升也會成倍放大。請閱讀文章:?.18、Netty的對象 怎么實現(xiàn)的?Netty 并沒有使用第 庫實現(xiàn)對象池,而是 實現(xiàn)了一個相對輕量的對象池。通過使用threadLocal,避免了多線程下取數(shù)據(jù)時可能出現(xiàn)的線程安全問題,同時,為了實現(xiàn)多線程回收同一個 實

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
  • 6. 下載文件中如有侵權(quán)或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論