Netty 簡(jiǎn)介

很早以前其實(shí)就寫過(guò)關(guān)于 Netty 的使用糯崎,最近發(fā)現(xiàn)在CSDN上一直有人在看很早寫的 Netty 文章河泳,個(gè)人感覺(jué)那時(shí)候?qū)懙暮艽植诓鸹樱掠绊懲械拈喿x質(zhì)量纸兔,但是我也不知道為啥有這么多小伙伴關(guān)注Netty汉矿,所以決定重新寫一些關(guān)于Netty的文章洲拇,補(bǔ)充以前的不足吧赋续。

Netty能做啥

簡(jiǎn)單說(shuō)就是用來(lái)處理網(wǎng)絡(luò)編程,寫一款能進(jìn)行網(wǎng)絡(luò)通信的服務(wù)端和客戶端程序蛾绎。

如果沒(méi)有 Netty秘通,在 Java 的世界中如何處理網(wǎng)絡(luò)編程呢敛熬?

Java自帶的工具有:java.net 包应民,用于處理網(wǎng)絡(luò)通信,后面Java提供了 NIO 工具包用于提供非阻塞的通信繁仁。
與Netty同級(jí)別的第三方工具包:Mina黄虱,在設(shè)計(jì)上與Netty 有些許不同捻浦,但是核心都是提供網(wǎng)絡(luò)通信的能力朱灿。

傳統(tǒng)網(wǎng)絡(luò)通信模型

說(shuō)Netty之前還是先講一下傳統(tǒng)的網(wǎng)絡(luò)編程是什么樣子盗扒。傳統(tǒng)的Socket編程開發(fā)步驟很簡(jiǎn)單侣灶,只需要使用Socket類創(chuàng)建客戶端和服務(wù)端即可褥影。但是為啥現(xiàn)在沒(méi)有人用它了呢伪阶?主要原因是它基于同步阻塞 IO 的線程模型去做的栅贴,在當(dāng)今時(shí)代完全不能滿足生產(chǎn)需要檐薯,自然被out墓猎。

1.png

同步阻塞線程模型的問(wèn)題在于一個(gè)請(qǐng)求必須綁定一個(gè)線程去處理毙沾,并且所有的請(qǐng)求都是同步操作宠页,意味著該請(qǐng)求未處理完之前這個(gè)連接不會(huì)被釋放举户,如果并發(fā)高的情況必然會(huì)導(dǎo)致系統(tǒng)壓力過(guò)大。

Netty 的新線程模型

基于此俭嘁,Java新增了非阻塞的IO操作包 NIO拐云, NIO 的線程模型采用了Reactor 模式慨丐,即異步非阻塞的方式房揭,解決了之前同步阻塞帶來(lái)的問(wèn)題捅暴。

NIO 的全稱是 NoneBlocking IO蓬痒,非阻塞 IO梧奢,區(qū)別與 BIO,BIO 的全稱是 Blocking IO鸟顺,阻塞 IO。那這個(gè)阻塞是什么意思呢兆沙?

  1. Accept是阻塞的葛圃,只有新連接來(lái)了装悲,Accept才會(huì)返回尚氛,主線程才能繼洞渤;
  2. Read是阻塞的阅嘶,只有請(qǐng)求消息來(lái)了,Read才能返回载迄,子線程才能繼續(xù)處理讯柔;
  3. Write是阻塞的,只有客戶端把消息收了护昧,Write才能返回魂迄,子線程才能繼續(xù)讀取下一個(gè)請(qǐng)求。

服務(wù)器在處理響應(yīng)的設(shè)計(jì)模式方面目前主要分為兩種:線程驅(qū)動(dòng)事件驅(qū)動(dòng)惋耙。同步阻塞就是線程驅(qū)動(dòng)的模式捣炬,最明顯的例子就是 Tomcat湿酸;對(duì)于事件驅(qū)動(dòng)來(lái)說(shuō),沒(méi)有必要為每一個(gè)連接都創(chuàng)建一個(gè)線程去維護(hù),參考觀察者模式,可以設(shè)置一個(gè)事件池襟铭,用一個(gè)單線程去循環(huán)監(jiān)聽(tīng)當(dāng)前池中是否有完成的事件哩都,如果有則取出該事件咐汞。

簡(jiǎn)單說(shuō)一下 Reactor 模式是如何解決線程等待問(wèn)題的:在等待IO的時(shí)候植阴,線程可以先退出不用一直等待IO操作。但是如果不等待那么IO處理完成之后返回給誰(shuí)呢?Reactor模型采用了事件驅(qū)動(dòng)機(jī)制,要求線程在退出前向event loop注冊(cè)回調(diào)函數(shù)剖淀,這樣IO完成之后 event loop 就可以調(diào)用回調(diào)函數(shù)完成數(shù)據(jù)返回捌刮。

在Reactor中有 4 個(gè)角色蛾派,所有的數(shù)據(jù)流入的處理統(tǒng)一稱為 Channel夜焦,就像是一個(gè)水管,Reactor 模型將每一種事件拆分為一個(gè) event,相同類型的 event 歸為一類,這一類的統(tǒng)一處理邏輯被稱為一個(gè) handler。那么怎么去讓一個(gè)或者多個(gè)線程去監(jiān)聽(tīng)所有的 Channel 呢查蓉? 所以就有 Selector鹃共,Selector 就像是一個(gè)管理者,你可以將多個(gè) Channel 注冊(cè)到 一個(gè)Selector 線程上,它會(huì)使用一個(gè)阻塞方法去捕獲當(dāng)前 Channel 上是否有事件發(fā)生,如果有則取出事件交給對(duì)應(yīng)的 handler 去處理毕泌。

Netty 是建立在 NIO 之上的辩诞,并且 Netty 在 NIO 上面又提供了更多高層次 API 的封裝。

為什么不用 JDK 提供的 NIO

JDK 已經(jīng)給我們提供了 NIO 的包伯顶,也是使用了 Reactor 模型來(lái)實(shí)現(xiàn)的異步非阻塞模式掐暮,那我們?yōu)樯对谌粘i_發(fā)中沒(méi)有聽(tīng)到誰(shuí)直接使用 NIO 來(lái)開發(fā)網(wǎng)絡(luò)編程呢瓢宦?實(shí)際上大家不使用的原因是因?yàn)樗y控制疲吸。Java NIO 類庫(kù)中主要提供的功能包括:

  • 緩沖區(qū) Buffer
  • 通道 Channel
  • 多路復(fù)用器 Selector

緩沖區(qū) Buffer 其實(shí)就是一個(gè)對(duì)象舰绘,即所有流入或者流出的數(shù)據(jù)都在Buffer中存在孵运。

新 IO 與老的面向流 IO 的區(qū)別在于老 IO 直接面向字節(jié)流進(jìn)行處理,新 IO 是面向緩沖區(qū)進(jìn)行處理蹂空,讀寫數(shù)據(jù)都是先讀寫到緩沖區(qū)中糖声。緩沖區(qū)實(shí)質(zhì)上是一個(gè)字節(jié)數(shù)組并扇,NIO 提供了對(duì)緩沖區(qū)數(shù)據(jù)讀寫位置維護(hù)的操作能力鬼雀。

2.jpg

Channel 通道,所有 Buffer內(nèi)的數(shù)據(jù)都會(huì)往 Channel 上流,數(shù)據(jù)通過(guò) Channel 留向處理邏輯阿纤,通過(guò) Channel 將處理過(guò)的數(shù)據(jù)返回給客戶端。所以 Channel 是全雙工的,可以支持讀寫屈呕,這是它與 Stream 的區(qū)別岳守。如果你使用Stream俊卤,讀數(shù)據(jù)只能使用 InputStream 進(jìn)行操作,寫數(shù)據(jù)只能使用 OutputStream 進(jìn)行操作记盒。用現(xiàn)實(shí)世界中的事物比喻的話,傳統(tǒng) IO 猶如水管熙尉,水流只能沿著管道往下流爱态; NIO 猶如一條雙向公路缚态,兩個(gè)方向都可以行車。

另外也正是因?yàn)?Buffer 的引入我們才能隨意的控制每次傳輸讀多少數(shù)據(jù)祈匙,如果上次讀取失敗,那么應(yīng)該從多少偏移量重新讀取腰素,這是傳統(tǒng) I/O流無(wú)法比擬的姻政。

Selector 選擇器,它是 NIO 的核心品洛,一個(gè) Selector 就是一個(gè)線程士飒,NIO 允許一個(gè) Selector 管理多個(gè) Channel,即將 Channel 注冊(cè)到 Selector 上萌壳,Selector 會(huì)去監(jiān)聽(tīng)注冊(cè)的 Channel 上是否有事件準(zhǔn)備就緒,如果有就取出處理。

4.png

關(guān)于 NIO 的代碼我就不寫了,是很龐大的一堆矛缨,大家百度一下就能看到述召⌒杂總之基于這個(gè)思想來(lái)進(jìn)行網(wǎng)絡(luò)編程肯定是面對(duì)當(dāng)今流量洪峰的最佳方式忌愚。而正好 Netty 底層基于 NIO 去做的封裝腊徙,已經(jīng)給你屏蔽了這一大坨操作胶逢。

網(wǎng)絡(luò)編程還有一個(gè)問(wèn)題就是跨平臺(tái)性初坠,NIO 底層是依賴系統(tǒng)的 IO API吴菠,不同的系統(tǒng)可能對(duì) IO API 的實(shí)現(xiàn)也是不一樣的榨乎,這里如何你使用 NIO 那么就需要考慮系統(tǒng)兼容性問(wèn)題了袍患。

另外還有一個(gè)問(wèn)題就是 NIO 有個(gè)很著名的 bug竣付,JDK 的 NIO 底層由 epoll 實(shí)現(xiàn)诡延,若Selector的輪詢結(jié)果為空,也沒(méi)有wakeup或新消息處理古胆,則發(fā)生空輪詢肆良,CPU 使用率100%。這個(gè) bug 官方聲明已經(jīng)修復(fù)逸绎,事實(shí)上沒(méi)有被 fix惹恃, 只是出現(xiàn)的概率會(huì)降低一些。

Netty 也對(duì)該 bug 進(jìn)行了處理:對(duì) Selector 的 select 操作周期進(jìn)行統(tǒng)計(jì)棺牧,每完成一次空的 select 操作進(jìn)行一次計(jì)數(shù)巫糙,若在某個(gè)周期內(nèi)連續(xù)發(fā)生N次空輪詢,則觸發(fā)了 epoll 死循環(huán)bug颊乘。那么這個(gè)時(shí)候就重建 Selector参淹,判斷是否是其他線程發(fā)起的重建請(qǐng)求,若不是則將原 SocketChannel 從舊的 Selector上去除注冊(cè)乏悄,重新注冊(cè)到新的 Selector 上浙值,并將原來(lái)的 Selector 關(guān)閉。

網(wǎng)絡(luò)編程應(yīng)該注意什么

既然說(shuō)要學(xué)習(xí) Netty檩小, 它本身是基于 NIO 的封裝用于網(wǎng)絡(luò)通信开呐,那么在編寫一段用于網(wǎng)絡(luò)通信的代碼我們應(yīng)該注意一些什么呢?弄清楚這些問(wèn)題识啦,我們大概就知道 Netty 都做了什么负蚊。

談到網(wǎng)絡(luò)就不能避免說(shuō)到 OSI 7層模型 和 TCP / IP 4層模型。

3.jpg

Java 網(wǎng)絡(luò)編程主要使用的是 Socket 套接字編程颓哮,基于 4層 協(xié)議的網(wǎng)絡(luò)編程家妆,即基于 TCP/ UDP 協(xié)議的封裝。編寫一個(gè) Socket 通信都有哪些步驟呢冕茅?

  1. 創(chuàng)建一個(gè) ServerSocket伤极,監(jiān)聽(tīng)并綁定一個(gè)端口蛹找;

  2. 一系列客戶端來(lái)請(qǐng)求這個(gè)端口;

  3. 服務(wù)器使用 Accept哨坪,獲得一個(gè)來(lái)自客戶端的Socket連接對(duì)象庸疾;

  4. 啟動(dòng)一個(gè)新線程處理連接;

    1. 讀 Socket当编,得到字節(jié)流届慈,
    2. 解碼協(xié)議,得到Http請(qǐng)求對(duì)象忿偷,
    3. 處理 HTTP 請(qǐng)求金顿,得到一個(gè)結(jié)果,封裝成一個(gè) HttpResponse 對(duì)象鲤桥,
    4. 編碼協(xié)議揍拆,將結(jié)果序列化字節(jié)流,
    5. 寫 Socket茶凳,將字節(jié)流發(fā)給客戶端嫂拴,
  5. 繼續(xù)循環(huán)步驟3。

根據(jù)以上的數(shù)據(jù)傳輸流程贮喧,我們可以提出一些問(wèn)題:

  1. 如何約定字節(jié)流長(zhǎng)度格式筒狠,以保證每次讀到的字節(jié)流都是最新的而不會(huì)和上次重復(fù);
  2. 傳輸字節(jié)流的編解碼問(wèn)題塞淹;
  3. 一個(gè)服務(wù)端肯定會(huì)有多個(gè)客戶端鏈接窟蓝,如何管理眾多的客戶端鏈接,比如如何維護(hù)斷線重連饱普,連接超時(shí)以及關(guān)閉機(jī)制运挫;

上面這些問(wèn)題我們?cè)诮酉聛?lái)的 Netty 學(xué)習(xí)中都會(huì)找到答案。

Netty 核心組件

在還未入門 Netty 之前我們先了解一下 Netty 里面都有哪些類套耕,做到有的放矢谁帕,后面學(xué)習(xí)帶著這些關(guān)鍵信息不回亂。

Bootstrap冯袍、ServerBootstrap

一個(gè) Netty 應(yīng)用通常由一個(gè) Bootstrap 開始匈挖,主要作用是配置整個(gè) Netty 程序,串聯(lián)各個(gè)組件康愤,Netty 中 Bootstrap 類是客戶端程序的啟動(dòng)引導(dǎo)類儡循,ServerBootstrap 是服務(wù)端啟動(dòng)引導(dǎo)類。

Future征冷、ChannelFuture

在 Netty 中所有的 IO 操作都是異步的择膝,不會(huì)立刻知道某個(gè)事件是否完成處理。但是可以過(guò)一會(huì)等它執(zhí)行完成或者直接注冊(cè)一個(gè)監(jiān)聽(tīng)检激,具體的實(shí)現(xiàn)就是通過(guò) Future 和 ChannelFutures肴捉,用來(lái)注冊(cè)一個(gè)監(jiān)聽(tīng)腹侣,當(dāng)操作執(zhí)行成功或失敗時(shí)監(jiān)聽(tīng)會(huì)自動(dòng)觸發(fā)注冊(cè)的監(jiān)聽(tīng)事件。

Channel

Netty 網(wǎng)絡(luò)通信的組件齿穗,能夠用于執(zhí)行網(wǎng)絡(luò) I/O 操作傲隶。Channel 為用戶提供:

  1. 當(dāng)前網(wǎng)絡(luò)連接的通道的狀態(tài)(例如是否打開,是否已連接)窃页;
  2. 網(wǎng)絡(luò)連接的配置參數(shù) (例如接收緩沖區(qū)大卸逯辍);
  3. 提供異步的網(wǎng)絡(luò) I/O 操作(如建立連接脖卖,讀寫帖鸦,綁定端口),異步調(diào)用意味著任何 I/O 調(diào)用都將立即返回胚嘲,并且不保證在調(diào)用結(jié)束時(shí)所請(qǐng)求的 I/O 操作已完成;
  4. 調(diào)用立即返回一個(gè) ChannelFuture 實(shí)例洛二,通過(guò)注冊(cè)監(jiān)聽(tīng)器到 ChannelFuture 上馋劈,可以 I/O 操作成功、失敗或取消時(shí)回調(diào)通知調(diào)用方晾嘶;
  5. 支持關(guān)聯(lián) I/O 操作與對(duì)應(yīng)的處理程序妓雾。

不同協(xié)議、不同的阻塞類型的連接都有不同的 Channel 類型與之對(duì)應(yīng)垒迂。

下面是一些常用的 Channel 類型:

1.  NioSocketChannel械姻,異步的客戶端 TCP Socket 連接;
2.  NioServerSocketChannel机断,異步的服務(wù)器端 TCP Socket 連接楷拳;
3.  NioDatagramChannel,異步的 UDP 連接吏奸;
4.  NioSctpChannel欢揖,異步的客戶端 Sctp 連接;
5.  NioSctpServerChannel奋蔚,異步的 Sctp 服務(wù)器端連接她混,這些通道涵蓋了 UDP 和 TCP 網(wǎng)絡(luò) IO 以及文件 IO。

Selector

Netty 基于 Selector 對(duì)象實(shí)現(xiàn) I/O 多路復(fù)用泊碑,通過(guò) Selector 一個(gè)線程可以監(jiān)聽(tīng)多個(gè)連接的 Channel 事件坤按。

當(dāng)向一個(gè) Selector 中注冊(cè) Channel 后,Selector 內(nèi)部的機(jī)制就可以自動(dòng)不斷地查詢 (Select) 這些注冊(cè)的 Channel 是否有已就緒的 I/O 事件(例如可讀馒过,可寫臭脓,網(wǎng)絡(luò)連接完成等),這樣程序就可以很簡(jiǎn)單地使用一個(gè)線程高效地管理多個(gè) Channel 沉桌。

NioEventLoop

NioEventLoop 中維護(hù)了一個(gè)線程和任務(wù)隊(duì)列谢鹊,支持異步提交執(zhí)行任務(wù)算吩,線程啟動(dòng)時(shí)會(huì)調(diào)用 NioEventLoop 的 run 方法,執(zhí)行 I/O 任務(wù)和非 I/O 任務(wù):

1.  I/O 任務(wù)佃扼,即 selectionKey 中 ready 的事件偎巢,如 accept、connect兼耀、read压昼、write 等,由 processSelectedKeys 方法觸發(fā)瘤运;
2.  非 IO 任務(wù)窍霞,添加到 taskQueue 中的任務(wù),如 register0拯坟、bind0 等任務(wù)但金,由 runAllTasks 方法觸發(fā)。

兩種任務(wù)的執(zhí)行時(shí)間比由變量 ioRatio 控制郁季,默認(rèn)為 50冷溃,則表示允許非 IO 任務(wù)執(zhí)行的時(shí)間與 IO 任務(wù)的執(zhí)行時(shí)間相等。

NioEventLoopGroup

NioEventLoopGroup梦裂,主要管理 eventLoop 的生命周期似枕,可以理解為一個(gè)線程池,內(nèi)部維護(hù)了一組線程年柠,每個(gè)線程 (NioEventLoop) 負(fù)責(zé)處理多個(gè) Channel 上的事件凿歼,而一個(gè) Channel 只對(duì)應(yīng)于一個(gè)線程。

ChannelHandler

ChannelHandler 是一個(gè)接口冗恨,處理 I/O 事件或攔截 I/O 操作答憔,并將其轉(zhuǎn)發(fā)到其 ChannelPipeline(業(yè)務(wù)處理鏈)中的下一個(gè)處理程序。

ChannelHandler 本身并沒(méi)有提供很多方法派近,因?yàn)檫@個(gè)接口有許多的方法需要實(shí)現(xiàn)攀唯,方便使用期間,可以繼承它的子類:

  1. ChannelInboundHandler 用于處理入站 I/O 事件渴丸;
  2. ChannelOutboundHandler 用于處理出站 I/O 操作侯嘀。

或者使用以下適配器類:

  1. ChannelInboundHandlerAdapter 用于處理入站 I/O 事件;
  2. ChannelOutboundHandlerAdapter 用于處理出站 I/O 操作谱轨;
  3. ChannelDuplexHandler 用于處理入站和出站事件戒幔。

ChannelHandlerContext

保存 Channel 相關(guān)的所有上下文信息,同時(shí)關(guān)聯(lián)一個(gè) ChannelHandler 對(duì)象土童。

ChannelPipline

保存 ChannelHandler 的 List诗茎,用于處理或攔截 Channel 的入站事件和出站操作。它實(shí)現(xiàn)了一種高級(jí)形式的攔截過(guò)濾器模式,使用戶可以完全控制事件的處理方式敢订,以及 Channel 中各個(gè)的 ChannelHandler 如何相互交互王污。在 Netty 中每個(gè) Channel 都有且僅有一個(gè) ChannelPipeline 與之對(duì)應(yīng)。

關(guān)于 Netty 的簡(jiǎn)介就先說(shuō)這么多楚午。下面的章節(jié)就帶著 Socket 通信應(yīng)該解決的問(wèn)題 和 上面提到的Netty關(guān)鍵組件我們一起看看Netty是如何實(shí)現(xiàn)高性能網(wǎng)絡(luò)通信的昭齐。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市矾柜,隨后出現(xiàn)的幾起案子阱驾,更是在濱河造成了極大的恐慌,老刑警劉巖怪蔑,帶你破解...
    沈念sama閱讀 219,039評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件里覆,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡缆瓣,警方通過(guò)查閱死者的電腦和手機(jī)喧枷,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,426評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)弓坞,“玉大人割去,你說(shuō)我怎么就攤上這事≈绯螅” “怎么了?”我有些...
    開封第一講書人閱讀 165,417評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵夸赫,是天一觀的道長(zhǎng)菩帝。 經(jīng)常有香客問(wèn)我,道長(zhǎng)茬腿,這世上最難降的妖魔是什么呼奢? 我笑而不...
    開封第一講書人閱讀 58,868評(píng)論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮切平,結(jié)果婚禮上握础,老公的妹妹穿的比我還像新娘。我一直安慰自己悴品,他們只是感情好苔严,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,892評(píng)論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著型将,像睡著了一般七兜。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上恬惯,一...
    開封第一講書人閱讀 51,692評(píng)論 1 305
  • 那天刹缝,我揣著相機(jī)與錄音言疗,去河邊找鬼。 笑死勤篮,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播竟终,決...
    沈念sama閱讀 40,416評(píng)論 3 419
  • 文/蒼蘭香墨 我猛地睜開眼喘鸟,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼崎淳!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,326評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤计福,失蹤者是張志新(化名)和其女友劉穎佩厚,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體筋讨,經(jīng)...
    沈念sama閱讀 45,782評(píng)論 1 316
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡壁袄,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,957評(píng)論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,102評(píng)論 1 350
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡漓概,死狀恐怖垛耳,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情飘千,我是刑警寧澤堂鲜,帶...
    沈念sama閱讀 35,790評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站护奈,受9級(jí)特大地震影響缔莲,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜霉旗,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,442評(píng)論 3 331
  • 文/蒙蒙 一痴奏、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧厌秒,春花似錦读拆、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,996評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至蚌讼,卻和暖如春辟灰,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背篡石。 一陣腳步聲響...
    開封第一講書人閱讀 33,113評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工芥喇, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人凰萨。 一個(gè)月前我還...
    沈念sama閱讀 48,332評(píng)論 3 373
  • 正文 我出身青樓继控,卻偏偏與公主長(zhǎng)得像械馆,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子湿诊,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,044評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容

  • 一狱杰、Netty概述 Netty是一個(gè)異步事件驅(qū)動(dòng)的網(wǎng)絡(luò)應(yīng)用框架,用于快速開發(fā)可維護(hù)的高性能協(xié)議服務(wù)器和客戶端厅须。 J...
    落地生涯閱讀 1,060評(píng)論 0 6
  • 一.JavaApi處理方式 ServerSocket serverSocket = new ServerSocke...
    何何與呵呵呵閱讀 942評(píng)論 0 0
  • BIO朗和、NIO和AIO的區(qū)別以及Netty 簡(jiǎn)介 要分清這三個(gè)错沽,首先要分清這兩組概念。 同步(Synchroniz...
    njitzyd閱讀 485評(píng)論 0 1
  • 本文轉(zhuǎn)載自本人個(gè)人博客與CSDN 1.簡(jiǎn)介 在本文中眶拉,我們將介紹Netty - 一個(gè)異步事件驅(qū)動(dòng)的網(wǎng)絡(luò)應(yīng)用程序框架...
    那個(gè)驢閱讀 528評(píng)論 0 0
  • 1.Netty是什么千埃? Netty是高性能、異步事件驅(qū)動(dòng)的非阻塞(NIO)Reactor模式的socket通信...
    匿名wm閱讀 1,455評(píng)論 0 1