日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

第一次听人用男女关系讲 N(Non-Blocking)I(进)O(出),涨姿势了

發布時間:2025/3/20 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 第一次听人用男女关系讲 N(Non-Blocking)I(进)O(出),涨姿势了 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
點擊上方?好好學java?,選擇?星標?公眾號重磅資訊,干貨,第一時間送達 今日推薦:推薦19個github超牛逼項目!個人原創100W +訪問量博客:點擊前往,查看更多

BIO:80 年代屌絲追妹

80 年代屌絲男買了一個 BP 機用來追妹,男士使用傳呼臺給女生留言:

男:下午一起看個電影?[早晨 10 點]

這是男生唯一心動的女生,所以一直守著自己的 BP 機,等待女生回復,就這樣一天過去了,直到:

男:BP 沒電,自動關機。

名詞解釋

  • BP 機和傳呼臺指的是 BIO 中的流單向傳輸的特性,屌絲男士通過傳呼臺給 BP 機發送消息是單向的,如果是女生通過傳呼臺回復屌絲男士,也是單向的。

  • 這個女生是男士唯一心動的女生,所以他傻等著 BP 機回復,即便可能一直不會有消息,這就是同步阻塞 IO,中 B 的概念。

  • BIO 的缺點

  • 同步阻塞 IO,如果存在多個請求的時候,服務端必須通過多線程處理,增加了服務端的壓力和創建銷毀線程的開銷。

  • 如果連接一直沒有響應,服務端也需要一直監聽端口等待,浪費了服務端資源。

  • NIO:80 年代公子哥把妹

    80 年代的公子哥買了一個大哥大,關鍵是這個公子哥太花心,同時中意了兩個妹子,于是他就開始了把妹過程。
    公子哥用大哥大給女 A 打電話:

    公子哥 -> 女 A:下午一起看個電影?[早晨 10 點]
    女 A -> 公子哥:我正在吃飯,你晚點再打過來?

    公子哥用大哥大給女 B 打電話:

    公子哥 -> 女 B:下午一起看個電影?[早晨 10 點 1 分]
    女 B -> 公子哥:我正在吃飯,你晚點再打過來?

    過了 10 分鐘公子哥再次打電話詢問

    公子哥 -> 女 A:怎么樣,有空嗎?[早晨 10 點 10 分]
    女 A -> 公子哥:我下午陪爸爸打馬球,不去了。
    公子哥 -> 女 B:怎么樣,有空嗎?[早晨 10 點 11 分]
    女 B -> 公子哥:好呀,下午 3 點來我家接我吧。
    公子哥 -> 女 B:好嘞,我開車去接你。

    最終公子哥成功了追求到了女 B,這個故事告訴我們,成功的前提是有錢。(你怎么看?)

    名詞解釋

  • 公子哥用上了大哥大,可以實現雙向的通話,這就是 NIO 中的 Channel,可以實現雙向的數據流傳輸。

  • 公子哥不用像 BP 機小哥一樣死等著回復,每次打電話都能得到回復,掛斷電話一會兒再來詢問即可,這就是 Channel 的非阻塞特性,也就是 “N” 的體現。

  • 公子哥可以同時撩兩個妹子,這就是 NIO 的 IO 多路復用,也就是 Selector。

  • 公子哥只能同時和一個人通話,這就是同步,所以 NIO 的全稱叫做同步非阻塞 IO。

  • 優缺點

  • 非阻塞 IO 模型,不需要阻塞在特定的請求。

  • 一個線程可以處理多個請求,不需要客戶端和服務器端一比一的對應,沒有多線程創建和銷毀帶來的系統開銷。

  • 服務端不需要死等請求,減少了服務端壓力。

  • 關鍵名詞

  • Channel,雙向傳輸,非阻塞的通道,有FileChannel,DatagramChannel,ServerSocketChannel/SocketChannel 等。

  • Buffer,數據塊的讀寫,可以理解字節數組,效率高。四個重要屬性:capacity 容量,position 位置, limit 上限,用戶切換讀寫時候的游標,mark 標記,標記 position 的位置,分為堆內內存和堆外內存,也是 NIO 性能的關鍵內容。

  • Selector,IO 多路復用的關鍵,實現了循環查看可以使用的 Channel,解決死等問題。

  • Selector 實現有多種方式,自己寫一個數組循環也是方式,也可以實現 IO 多路復用,只是性能好壞而已,所以基于底層 poll、select和epoll 也是實現“遍歷”可用通道的方式不同而已。select 使用輪詢的方式,有 1024 個連接的限制,poll 去掉了這個限制依然是輪詢的方式,epoll 是基于系統的注冊回調的方式,監聽系統的事件實現。

  • NIO 引入了 Buffer 的概念,每次使用 Buffer 拷貝數據其實是一次從用戶空間(JVM) 向系統空間(系統內存) 的一次拷貝, Java 里面提供了 DirectByteBuffer 堆外內存,如果使用使用堆外內存,可以減少一次系統空間和用戶空間的拷貝,這種現象叫做零拷貝。強調一下,并不是操作系統不能直接操作 HeapByteBuffer(對內內存),而且在 GC 的作用下,內存地址可能隨時變化,操作的內存數據不一定準備。

  • IO 多路復用性能更好,針對的 I/O 密集型應用程序,如果是 CPU 密集型應用程序,還是通過多線程的方案。所以很多寫 IO 多路復用的文章都會說“多線程的創建,必然存在創建銷毀和切換的開銷,在高并發系統中,會拖慢整個系統”,其實并不是非常的準確,雖然是想說明 I/O 多路復用的利好,但是確實有點以偏概全。

  • AIO:21 世紀非智能時代大學生把妹

    21 世紀初期,還沒有智能機,不過諾基亞 1110 砸核桃神機已經普及了,下面就是新時代大學生小王用自己的諾基亞 1110 的把妹過程。
    小王給中意的兩個女生直接發短信留言(群發):

    小王 -> 女 A:下午一起看個電影?[早晨 10 點]
    小王 -> 女 B:下午一起看個電影?[早晨 10 點]

    發完短信小王去看《西游記》去了。10分鐘以后電話響起,收到了妹子的短信,小王拿起了手機閱讀了消息并進行回復。

    女 B -> 小王:好呀,下午 3 點來我家接我吧 [早晨 10 點 10 分]
    小王 -> 女 B:好的,我去接你不見不散。

    名詞解釋

  • 小王發完短信不需要盯著手機看,也不需要時不時看一下手機,有短信回復會有通知,再來閱讀就好了。這就是 AIO 中的 AsynchronousServerSocketChannel,可以注冊一個回調 CompletionHandler,等待有消息的時候直接通知回調處理即可。

  • 優缺點

    AIO 包括了 NIO 的所有優缺點的同時,增加了異步回調的能力,由此解決的問題是不需要同步的等待非阻塞 IO 的反饋,所以 NIO 叫做異步非阻塞 IO 模型。

    是時候展示真正的技術了

    說了這么多,用 NIO 實現一個把妹聊天程序唄?

    服務器端

    public?class?NioServer?{public?void?start()?throws?IOException?{Selector?selector?=?Selector.open();ServerSocketChannel?serverSocketChannel?=?ServerSocketChannel.open();serverSocketChannel.bind(new?InetSocketAddress(6789));serverSocketChannel.configureBlocking(false);serverSocketChannel.register(selector,?SelectionKey.OP_ACCEPT);System.out.println("服務器啟動成功");while?(true)?{selector.select();Set<SelectionKey>?selectionKeys?=?selector.selectedKeys();Iterator<SelectionKey>?iterator?=?selectionKeys.iterator();while?(iterator.hasNext())?{SelectionKey?selectionKey?=?iterator.next();if?(selectionKey.isAcceptable())?{iterator.remove();handleAccept(serverSocketChannel,?selector);}?else?if?(selectionKey.isReadable())?{handleRead(selectionKey);}?else?{System.out.println("其他請求");}}}}private?void?handleRead(SelectionKey?selectionKey)?throws?IOException?{SocketChannel?socketChannel?=?(SocketChannel)?selectionKey.channel();ByteBuffer?byteBuffer?=?ByteBuffer.allocate(1024);StringBuilder?request?=?new?StringBuilder();while?(socketChannel.read(byteBuffer)?>?0)?{byteBuffer.flip();request.append(StandardCharsets.UTF_8.decode(byteBuffer));}if?(request.length()?>?0)?{System.out.println("服務端收到消息:"?+?request.toString());}}private?void?handleAccept(ServerSocketChannel?serverSocketChannel,?Selector?selector)?throws?IOException?{SocketChannel?socketChannel?=?serverSocketChannel.accept();socketChannel.configureBlocking(false);socketChannel.register(selector,?SelectionKey.OP_READ);System.out.println("有新人進入聊天室");socketChannel.write(StandardCharsets.UTF_8.encode("進入聊天室,現在可以聊天了"));}public?static?void?main(String[]?args)?throws?IOException?{new?NioServer().start();} }

    客戶端

    public?class?NioClient?{public?void?start()?throws?IOException?{SocketChannel?socketChannel?=?SocketChannel.open(new?InetSocketAddress(6789));Selector?selector?=?Selector.open();socketChannel.configureBlocking(false);socketChannel.register(selector,?SelectionKey.OP_READ);new?Thread(new?NioClientHandler(selector)).start();Scanner?scanner?=?new?Scanner(System.in);while?(scanner.hasNextLine())?{String?request?=?scanner.nextLine();if?(request?!=?null?&&?request.length()?>?0)?{socketChannel.write(StandardCharsets.UTF_8.encode(request));}}}public?static?void?main(String[]?args)?throws?IOException?{new?NioClient().start();}private?class?NioClientHandler?implements?Runnable?{private?Selector?selector;public?NioClientHandler(Selector?selector)?{this.selector?=?selector;}@Overridepublic?void?run()?{try?{while?(true)?{selector.select();Set<SelectionKey>?selectionKeys?=?selector.selectedKeys();Iterator?iterator?=?selectionKeys.iterator();while?(iterator.hasNext())?{SelectionKey?selectionKey?=?(SelectionKey)?iterator.next();SocketChannel?socketChannel?=?(SocketChannel)?selectionKey.channel();ByteBuffer?byteBuffer?=?ByteBuffer.allocate(1024);StringBuilder?response?=?new?StringBuilder();while?(socketChannel.read(byteBuffer)?>?0)?{byteBuffer.flip();response.append(StandardCharsets.UTF_8.decode(byteBuffer));}if?(response.length()?>?0)?{System.out.println("接收服務端消息:"?+?response);}}}}?catch?(Exception?e)?{e.printStackTrace();}}} }

    參考文檔

  • 圖解 | 深入揭秘 epoll 是如何實現 IO 多路復用的!

  • 解鎖網絡編程之NIO的前世今生

  • NIO如何實現多路復用?

  • 深入理解 Java IO

  • 高并發專題之 IO 多路復用:Select、Poll、Epoll

  • 推薦文章
    • 面試官問:前后端分離項目,有什么優缺點?我說:沒

    • 2020 年騰訊新增 20 億行代碼,鵝廠第一編程語言還是它

    • 通俗講解分布式鎖,看完不懂算我輸

    • 寫博客能月入10K?

    • 一款基于 Spring Boot 的現代化社區(論壇/問答/社交網絡/博客)

    更多項目源碼
    • 這或許是最美的Vue+Element開源后臺管理UI

    • 推薦一款高顏值的 Spring Boot 快速開發框架

    • 一款基于 Spring Boot 的現代化社區(論壇/問答/社交網絡/博客)

    • 13K點贊都基于 Vue+Spring 前后端分離管理系統ELAdmin,大愛

    • 想接私活時薪再翻一倍,建議根據這幾個開源的SpringBoot項目

    總結

    以上是生活随笔為你收集整理的第一次听人用男女关系讲 N(Non-Blocking)I(进)O(出),涨姿势了的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。