固定內存分配
的全局對象,也就是說要放到緩存區中的字節數須要提早肯定Buffer 類的實例相似於整數數組,但 Buffer 的大小是固定的、且在 V8 堆外分配物理內存。 Buffer 的大小在被建立時肯定,且沒法調整。javascript
Buffer 類在 Node.js 中是一個全局變量,所以無需使用 require('buffer').Buffer。前端
怎麼建立buffer? 第一種方式:Buffer.alloc()
java
let buffer = Buffer.alloc(6);
//建立一個長度爲6,而且用0填充的Buffer。
//這樣申請方式,內存永遠是乾淨的。
// 這種聲明也比較耗時,由於聲明以後,還要把裏面的東西手動清空
//輸出:<Buffer 00 00 00 00 00 00>
let buffer2 = Buffer.alloc(6,1);
// 建立一個長度爲 六、且用 0x1 填充的 Buffer。
//輸出:<Buffer 01 01 01 01 01 01>
複製代碼
第二種方式:Buffer.allocUnsafe()
編程
let buffer = Buffer.allocUnsafe(6);
// 建立一個長度爲 六、且未初始化的 Buffer。
// 這個方法比調用 Buffer.alloc() 更快
//輸出:<Buffer 07 00 00 00 00 00>
//但裏面的東西是不安全的,可能含有舊數據。
//所以須要使用 fill() 或 write() 重寫
buffer.fill(0);//對buffer進行重寫
//輸出:<Buffer 00 00 00 00 00 00>
複製代碼
// 建立一個長度爲 十、且用 0 填充的 Buffer。
let buf1 = Buffer.alloc(10);
// 建立一個長度爲 十、且用 0x1 填充的 Buffer。
let buf2 = Buffer.alloc(10, 1);
// 建立一個長度爲 十、且未初始化的 Buffer。
let buf3 = Buffer.allocUnsafe(10);
複製代碼
let buf = Buffer.from('hello world');
//輸出:<Buffer 68 65 6c 6c 6f 20 77 6f 72 6c 64>
//默認是轉成utf8格式的數據,也能夠轉成其餘格式的數據,不支持gbk
複製代碼
3 經過數組定義數組
let buf = Buffer.from([1, 2, 3]);
// 建立一個包含 [0x1, 0x2, 0x3] 的 Buffer。
//<Buffer 01 02 03>
let buf2 = Buffer.from([16, 17, 18]);
//<Buffer 10 11 12>
//Buffer存的都是16進制,可是form存放的都是10進制,因此要除以16
複製代碼
以上3種方法,是建立buffer的3種方式緩存
buf.write(string[, offset[, length]][, encoding])
安全
好比有個字符串'我愛編程',但願將我和愛編程分開輸出,也就是第一次將我放到一個變量裏,把剩餘3個字放到一個變量裏。 具體操做:ui
// 先申請一個Buffer
// 一個漢字3個字節,4個漢字12個字節
let buffer = Buffer.alloc(12);//裏面是0填充的,內存是乾淨的
// 再構建兩個buf1和buf2,而後把他們寫到第一個個buffer裏
let buf1 = '我';
let buf2 = '愛編程';
// write的參數分別是:寫入的內容 ,偏移量,長度,編碼格式
buffer.write(buf1,0,3,'utf8');//往buffer裏面寫內容buf1,從當前buffer的開頭寫,因此是第0個,長度是3,由於一個漢字3個字節
// 再寫一個buf2
buffer.write(buf2,3,9,'utf8');
console.log(buffer);
//<Buffer e6 88 91 e7 88 b1 e7 bc 96 e7 a8 8b>
// 把buffer和字符串進行轉換
console.log(buffer.toString());
//我愛編程
複製代碼
任意進制字符串
轉換爲十進制
parseInt("11", 2); // 3 2進制轉10進制
parseInt("77", 8); // 63 8進制轉10進制
parseInt("e7", 16); //175 16進制轉10進制
複製代碼
10進制
轉換爲其它進制字符串
(3).toString(2)) // "11" 十進制轉2進制
(17).toString(16) // "11" 十進制轉16進制
(33).toString(32) // "11" 十提製轉32進制
複製代碼
buf.slice([start[, end]]);this
start
: 新建的 Buffer 開始的位置。 默認: 0end
: 新建的 Buffer 結束的位置(不包含)。 默認: buf.length<Buffer>
let buffer = Buffer.alloc(6);
let newBuffer = buffer.slice(0,3);
newBuffer[0] = 100;
console.log(buffer)
//<Buffer 64 00 00 00 00 00>
//因而可知,buffer裏面存的是內存地址
複製代碼
target
<Buffer>
| <Uint8Array>
要拷貝進的 Buffer 或 Uint8Array。targetStart
target 中開始拷貝進的偏移量。 默認: 0sourceStart
buf 中開始拷貝的偏移量。 當 targetStart 爲 undefined 時忽略。 默認: 0sourceEnd
buf 中結束拷貝的偏移量(不包含)。 當 sourceStart
爲 undefined
時忽略。 默認: buf.length<integer>
被拷貝的字節數。拷貝 buf 的一個區域的數據到 target 的一個區域,即使 target 的內存區域與 buf 的重疊。編碼
let buffer = Buffer.alloc(6);
let buf1 = Buffer.from('一');
let buf2 = Buffer.from('萬');
//要打印出萬一
// 要把buf2 buf1的內容拷貝到buffer中
// write和copy的區別:write拷的是字符串,copy拷的是buffer
// 參數:目標 target中開始拷貝進的偏移量 buf1中開始拷貝的偏移量 buf1中結束拷貝的偏移量(不包含)
buf1.copy(buffer,3,0,3);//由於一時第二個文字,因此寫在第3位(一個文字3個字節,第一個文字被佔用,即012被佔用)
buf2.copy(buffer,0,0,3);
console.log(buffer.toString())
//輸出:萬一
複製代碼
那麼問題來了,如何實現copy方法? 首先,copy是Buffer實例上的方法,因此應該定義在Buffer原型上。
Buffer.prototype.mycopy = function(target, targetStart, sourceStart, sourceEnd){
/** * 有4個參數 * 目標 * target中開始拷貝進的偏移量 * buf1中開始拷貝的偏移量 * buf1中結束拷貝的偏移量(不包含) * */
//Buffer跟數組很像,有個迭代的功能
for(let i = sourceStart;i<sourceEnd; i++){//迭代每一項
// 從偏移量開始寫
target[i+targetStart] = this[i]; //迭代每一項賦給目標buffer,this是buf1實例
}
}
buf1.mycopy(buffer,3,0,3);//由於一時第二個文字,因此寫在第3位(一個文字3個字節,第一個文字被佔用,即012被佔用)
buf2.mycopy(buffer,0,0,3);
console.log(buffer.toString())
複製代碼
list
< Array > 要合併的 Buffer
或 Uint8Array 實例的數組totalLength
< integer > 合併時 list
中 Buffer
實例的總長度返回一個合併了 list 中全部 Buffer 實例的新建的 Buffer 。 若是 list 中沒有元素、或 totalLength 爲 0 ,則返回一個新建的長度爲 0 的 Buffer 。 若是沒有提供 totalLength ,則從 list 中的 Buffer 實例計算獲得。 爲了計算 totalLength 會致使須要執行額外的循環,因此提供明確的長度會運行更快。 若是提供了 totalLength,totalLength 必須是一個正整數。若是從 list 中計算獲得的 Buffer 長度超過了 totalLength,則合併的結果將會被截斷爲 totalLength 的長度。
let buffer1 = Buffer.from('前');
let buffer2 = Buffer.from('端');
let buffer = Buffer.concat([buffer1,buffer2]).toString();//返回的是新Buffer,要toString()轉譯一下
console.log(buffer);
//輸出:前端
let buf = Buffer.concat([buffer1,buffer2],10).toString();
console.log(buf);
//若是把長度寫多了,會有問題,見下圖
//多寫的內容就是0
複製代碼
split
value
< string > | < Buffer > | < Uint8Array > | < integer > 要搜索的值byteOffset
< integer > buf 中開始搜索的位置。默認: 0encoding
< string > 若是 value 是一個字符串,則這是它的字符編碼。 默認: 'utf8'value
首次出現的索引,若是 buf 沒包含 value
則返回 -1若是 value
是:
value
根據 encoding 的字符編碼進行解析。Buffer
或 Uint8Array
,則 value
會被做爲一個總體使用。若是要比較部分 Buffer
,可以使用 buf.slice()。value
會解析爲一個 0 至 255 之間的無符號八位整數值。const buf = Buffer.from('this is a buffer');
// 輸出: 0
console.log(buf.indexOf('this'));
// 輸出: 2
console.log(buf.indexOf('is'));
// 輸出: 8
console.log(buf.indexOf(Buffer.from('a buffer')));
// 輸出: 8
// (97 是 'a' 的十進制 ASCII 值)
console.log(buf.indexOf(97));
// 輸出: -1
console.log(buf.indexOf(Buffer.from('a buffer example')));
// 輸出: 8
console.log(buf.indexOf(Buffer.from('a buffer example').slice(0, 8)));
const utf16Buffer = Buffer.from('\u039a\u0391\u03a3\u03a3\u0395', 'ucs2');
// 輸出: 4
console.log(utf16Buffer.indexOf('\u03a3', 0, 'ucs2'));
// 輸出: 6
console.log(utf16Buffer.indexOf('\u03a3', -4, 'ucs2'));
複製代碼