node:buffer
NodeJs 的 buffer 模块
Buffer
buffer 模块中提供了 Buffer 对象,用于开发者操作缓冲区。它也被直接暴露在了全局作用域当中
import buffer from 'node:buffer'
console.log(buffer.Buffer === Buffer) //=> true创建一个缓冲区
使用 Buffer.from() 来创建缓冲区(new Buffer() 在 NodeJs 6 之后就不推荐使用了)
创建的四种形式
Buffer.from(string[, encoding])Buffer.from(array)Buffer.from(buffer)Buffer.from(arrayBuffer[, byteOffset[, length]])
const buf = Buffer.from("hello buffer")
console.log(buf) //=> <Buffer 68 65 6c 6c 6f 20 62 75 66 66 65 72>
// 指定编码:
console.log(Buffer.from('peterroe', 'utf8'));
//=> <Buffer 70 65 74 65 72 72 6f 65>
console.log(Buffer.from('peterroe', 'utf16le'));
//=> <Buffer 70 00 65 00 74 00 65 00 72 00 72 00 6f 00 65 00>
console.log(Buffer.from('tést', 'latin1'));
//=> <Buffer 74 e9 73 74>
// 写的数据默认会被转为 2位 16进制
console.log(Buffer.from([255,3,44,0b101,0x44])) //=> <Buffer ff 03 2c 05 44>
// 超过 255 会溢出,从 0 重新开始计数(相当于执行了:value & 255)
console.log(Buffer.from([257, 3,44,3])) //=> <Buffer 01 03 2c 03>
// 输入十六进制
console.log(Buffer.from("2acb", "hex")) //=> <Buffer 2a cb>
// 奇数长度被截断
console.log(Buffer.from("2ac", "hex")) //=> <Buffer 2a>
// 非十六进制字符被截断
console.log(Buffer.from('1ag123', 'hex')) //=> <Buffer 1a>如果在创建的时候,还没有准备好数据,可以使用 Buffer.alloc() 来申请一个空间,但是并不写入数据
const buf = Buffer.alloc(10)写入数据
通过 .write() 可以写入数据
// ✅ 正确用法:
const buf = Buffer.alloc(100)
buf.write("hello buffer")
// ❌ 错误用法:
const buf = Buffer.from("hello buffer")
// 通过 Buffer.from 创建的 buf,再写入数据是无效的
buf.write("data")填充数据
类似于字符串的 .fill()
const b = Buffer.alloc(10).fill('a')
console.log(b.toString())
//=> This will print aaaaaaaaaa输出
提供了 toString()
type BufferEncoding = 'ascii'| 'utf8'| 'utf-8'| 'utf16le'| 'ucs2'| 'ucs-2'| 'base64'| 'base64url'| 'latin1'| 'binary'| 'hex';
console.log(Buffer.from("hello")) //=> <Buffer 68 65 6c 6c 6f>
console.log(Buffer.from("hello").toString()) //=> hello
console.log(Buffer.from("hello").toString('utf8')) //=> hello
console.log(Buffer.from([10,50,255]).toString('hex')) //=> 0a32ff
console.log(Buffer.from("peterroe").toString("base64")) //=> cGV0ZXJyb2U=原型链
TypedArray
上面我们看到, Buffer 集成自 TypedArray,实际上 NodeJs 全局作用域中并不存在 TypedArray 这个对象,或者说允许通过 new TypedArray() 调用
在 MDN-TypedArray 中有说明:
1.TypedArray 对象描述了底层二进制数据缓冲区的类似数组的视图
2.有许多不同的全局属性,其值是特定元素类型的类型化数组构造函数
上面引用的第一点说明,我们可以通过类似遍历数组的方法来访问 Buffer 实例的每一项,而且这些方法并不来源于 Array
const buf = Buffer.from('xyz');
buf.forEach()
for (let [i, it] of buf.entries()) {
console.log([i, it]); // it: ASCII 中的编号
// [ 0, 120 ]
// [ 1, 121 ]
// [ 2, 122 ]
}
console.log(buf instanceof Array) // => false关于上面引用的第二点,NodeJs 提供了一系列的 TypedArray 对象,下面每一项都可以被称为特定类型的 TypedArray
| Type | Value Range | Size in bytes | Web IDL type |
|---|---|---|---|
| Int8Array | -128 to 127 | 1 | byte |
| Uint8Array | 0 to 255 | 1 | octet |
| Uint8ClampedArray | 0 to 255 | 1 | octet |
| Int16Array | -32768 to 32767 | 2 | short |
| Uint16Array | 0 to 65535 | 2 | unsigned short |
| Int32Array | -2147483648 to 2147483647 | 4 | long |
| Uint32Array | 0 to 4294967295 | 4 | unsigned long |
| Float32Array | -3.4e38 to 3.4e38 | 4 | unrestricted float |
| Float64Array | -1.8e308 to 1.8e308 | 8 | unrestricted double |
| BigInt64Array | -2^63 to 2^63 - 1 | 8 | bigint |
| BigUint64Array | 0 to 2^64 - 1 | 8 | bigint |
由原型链看来,我们的 Buffer,就是 Uint8Array 的一员,所以也有:
const buf = Buffer.alloc(10)
console.log(buf instanceof Uint8Array) //=> trueBuffers and TypedArrays
const arr = new Uint16Array(2);
arr[0] = 5000; // 相当于 0x1388
arr[1] = 4000; // 相当于 0xfa0
// 拷贝 arr 的内容.
const buf1 = Buffer.from(arr);
// 共享 arr 的内存
const buf2 = Buffer.from(arr.buffer);
console.log(buf1) // 默认创建的就是两位16进制,所以会被截断
// Prints: <Buffer 88 a0>
console.log(buf2)
// Prints: <Buffer 88 13 a0 0f>
arr[1] = 6000; // 相当于 0x1770
console.log(buf1);
// Prints: <Buffer 88 a0>
console.log(buf2);
// Prints: <Buffer 88 13 70 17>ArrayBuffer
我们来介绍名字和 Buffer 有点像的 ArrayBuffer,后者与前者一个非常大的不同是,后者在浏览器和 NodeJs 环境都存在,但是使用起来有差别
ArrayBuffer对象用于表示通用的原始二进制数据缓冲区,它的定义非常原始和基础,所以我们要借助 TypedArray 来以特定的格式读取它的实例
const buffer = new ArrayBuffer(8);
const float32 = new Float32Array(buffer, 0, 2);
const unit8 = new Uint8Array(buffer, 0, 2);
console.log(float32.byteLength); // 8
console.log(float32); // [ 0, 0 ]
console.log(unit8.byteLength); // 2
console.log(unit8); // [ 0, 0 ]
let buf = Buffer.from(buffer)
buf.write('hello')
console.log(buf) // <Buffer 68 65 6c 6c 6f 00 00 00>ArrayBuffer 在 NodeJs 中并不常创建使用,通常是利用 TypedArray 处理接收外部的数据