偷偷摘套内射激情视频,久久精品99国产国产精,中文字幕无线乱码人妻,中文在线中文a,性爽19p

沒吃透Netty 緩沖區(qū),還能算得上Java老司機(jī)?

開發(fā) 后端
操作系統(tǒng)為了提供穩(wěn)定性,把虛擬地址空間分為用戶空間和內(nèi)核空間,其中用戶進(jìn)程只能操作用戶空間的內(nèi)容,而內(nèi)核空間的內(nèi)容可以操作用戶空間的內(nèi)容以及用戶空間的內(nèi)容。

 本文轉(zhuǎn)載自微信公眾號「小明菜市場」,作者小明菜市場。轉(zhuǎn)載本文請聯(lián)系小明菜市場公眾號。

前言

Java NIO 需要理解的主要有緩沖區(qū),通道,選擇器,這三個(gè)主要的部分。

基礎(chǔ)

用戶空間和內(nèi)核空間

操作系統(tǒng)為了提供穩(wěn)定性,把虛擬地址空間分為用戶空間和內(nèi)核空間,其中用戶進(jìn)程只能操作用戶空間的內(nèi)容,而內(nèi)核空間的內(nèi)容可以操作用戶空間的內(nèi)容以及用戶空間的內(nèi)容。

I/O過程中的數(shù)據(jù)流向

假設(shè)我們需要從磁盤中的某個(gè)文件讀取數(shù)據(jù),進(jìn)程發(fā)起read系統(tǒng)調(diào)用,進(jìn)入內(nèi)核狀態(tài),內(nèi)核會隨即向磁盤控制硬件發(fā)出命令,要求其從磁盤讀取數(shù)據(jù),磁盤控制器把數(shù)據(jù)直接寫入到內(nèi)核緩沖區(qū)中,隨后內(nèi)核會吧數(shù)據(jù)從內(nèi)核空間的臨時(shí)緩沖區(qū)拷貝到用戶緩沖區(qū),進(jìn)程再次切換回用戶態(tài)繼續(xù)執(zhí)行??偨Y(jié)數(shù)據(jù)流向是:磁盤 -> 內(nèi)核緩沖區(qū) -> 用戶緩沖區(qū)

內(nèi)存空間多重映射

對于虛擬地址的空間,一個(gè)以上的虛擬地址可以指向同一個(gè)物理內(nèi)存地址。如果用戶空間的虛擬地址和內(nèi)核空間的虛擬地址映射到同一個(gè)物理地址,那么這塊物理地址代表的空間就對內(nèi)核和用戶進(jìn)程都可見。便可省去數(shù)據(jù)在內(nèi)核緩沖區(qū)和用戶緩沖區(qū)來回復(fù)制的開銷。

緩沖區(qū)

Java NIO 數(shù)據(jù)傳輸過程,數(shù)據(jù)先放到發(fā)送緩沖區(qū) -> 通過通道發(fā)送到接收端 -> 接受端通道接受數(shù)據(jù)并填充到接受緩沖區(qū) 所以緩沖區(qū)的作用其實(shí)是連接通道作為數(shù)據(jù)傳輸?shù)哪繕?biāo)或者來源。

核心概念

屬性

需要理解Buffer工作機(jī)制,需要了解如下幾個(gè)屬性

  1. 容量: 緩沖區(qū)的容量,創(chuàng)建緩沖區(qū)時(shí)指定
  2. 位置: 下一個(gè)要被讀取或者寫入元素的索引
  3. 上界: 緩沖區(qū)中第一個(gè)不能被讀或者寫的位置。
  4. mark標(biāo)記,一個(gè)備忘的位置

存取

緩沖區(qū)的核心就在于存取操作,buffer提供了相對位置存取和絕對位置存取兩種方式。

  1. 相對位置存?。涸诋?dāng)前的位置寫入或者讀取數(shù)據(jù),然后增加位置的值。
  2. 絕對位置存取。在指定的位置的寫入或者讀取數(shù)據(jù),不改變位置的值

代碼如下

  1. //相對位置存取 
  2.  public abstract ByteBuffer put(byte b); 
  3.  public abstract byte get(); 
  4.  
  5.  //絕對位置存取 
  6.  public abstract ByteBuffer put(int index, byte b); 
  7.  public abstract byte get(int index); 

翻轉(zhuǎn)

翻轉(zhuǎn)是 buffer的核心概念,可以理解buffer有兩種模式,寫模式和讀模式。寫模式:我們分配一個(gè)緩沖區(qū),然后直接填充數(shù)據(jù),讀模式下。我們從頭開始讀取數(shù)據(jù)。如何從寫模式切換到讀模式,翻轉(zhuǎn),翻轉(zhuǎn)的時(shí)候我們用limit記錄待讀取數(shù)據(jù)的長度,然后把位置置換為0就可以開始讀取數(shù)據(jù)了。

  1. public final Buffer flip() { 
  2.    //記錄待讀取數(shù)據(jù)的長度 
  3.     limit = position; 
  4.    //從頭開始讀取數(shù)據(jù) 
  5.     position = 0; 
  6.     mark = -1; 
  7.     return this; 

demo

  1. //創(chuàng)建一個(gè)緩沖區(qū)  
  2. ByteBuffer buffer = ByteBuffer.allocate(100); 
  3. //寫數(shù)據(jù) 
  4. for (char c : "hello".toCharArray()) { 
  5.   buffer.put((byte) c); 
  6. //翻轉(zhuǎn) 
  7. buffer.flip();//等價(jià)于 buffer.limit(buffer.position()).position(0); 
  8. //讀數(shù)據(jù) 
  9. while (buffer.hasRemaining()) { 
  10.   char c = (char) buffer.get(); 
  11.   System.out.println(c); 

直接緩沖區(qū)

對于一般的I/O過程,數(shù)據(jù)流向是,磁盤或者網(wǎng)絡(luò) -> 內(nèi)核臨時(shí)緩沖區(qū) -> 用戶空間緩沖區(qū)

直接緩沖區(qū)解決的是內(nèi)核空間臨時(shí)緩沖區(qū)到用戶空間緩沖區(qū)復(fù)制這一步耗費(fèi)的多余。雖然直接緩沖區(qū)是I/O的最佳選擇,但是其比創(chuàng)建非直接緩沖區(qū)將會耗費(fèi)更大的成本了,所以一般都是直接重復(fù)使用。

創(chuàng)建緩沖區(qū)

Buffer不能直接通過構(gòu)造函數(shù)實(shí)例化,都是通過靜態(tài)工廠方法創(chuàng)建,下為ByteBuffer的靜態(tài)工廠方法。

  1. //創(chuàng)建內(nèi)存緩沖區(qū) 
  2. public static ByteBuffer allocate(int capacity); 
  3. //創(chuàng)建直接緩沖區(qū) 
  4. public static ByteBuffer allocateDirect(int capacity) ; 
  5.  
  6. public static ByteBuffer wrap(byte[] array, int offset, int length) 

 

責(zé)任編輯:武曉燕 來源: 小明菜市場
相關(guān)推薦

2019-08-20 09:30:18

Spring Clou組件Eureka

2011-12-14 16:30:42

javanio

2017-01-09 17:03:34

2019-02-27 13:58:29

漏洞緩沖區(qū)溢出系統(tǒng)安全

2017-07-04 17:09:10

Map環(huán)形緩沖區(qū)數(shù)據(jù)

2014-07-30 11:21:46

2018-01-26 14:52:43

2009-11-16 17:26:17

Oracle優(yōu)化緩沖區(qū)

2009-11-16 17:08:59

Oracle日志緩沖區(qū)

2018-08-15 10:29:58

NettyJDK內(nèi)存

2021-02-09 10:07:23

面試MySQL存儲

2009-07-15 15:50:48

Jython線程

2009-11-16 16:59:24

Oracle優(yōu)化庫高速

2023-10-09 23:01:09

MySQL數(shù)據(jù)庫

2009-09-24 18:16:40

2011-07-20 10:54:14

C++

2010-12-27 10:21:21

2017-12-07 16:13:18

程序員編程代碼

2015-03-06 17:09:10

2022-05-07 08:27:42

緩沖區(qū)溢出堆棧
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號