1. A Bufferhanyalah tampilan untuk melihat ke dalam ArrayBuffer.
A Buffer, pada kenyataannya, adalah a FastBuffer, yang extends(mewarisi dari) Uint8Array, yang merupakan tampilan satuan oktet ("pengakses parsial") dari memori aktual, an ArrayBuffer.
📜 Node.js 9.4.0/lib/buffer.js#L65-L73
class FastBuffer extends Uint8Array {
constructor(arg1, arg2, arg3) {
super(arg1, arg2, arg3);
}
}
FastBuffer.prototype.constructor = Buffer;
internalBuffer.FastBuffer = FastBuffer;
Buffer.prototype = FastBuffer.prototype;
2. Ukuran ArrayBufferdan ukuran tampilan dapat bervariasi.
Alasan # 1: Buffer.from(arrayBuffer[, byteOffset[, length]]).
Dengan Buffer.from(arrayBuffer[, byteOffset[, length]]), Anda dapat membuat Bufferdengan menentukan dasarnya ArrayBufferdan posisi serta ukuran tampilan.
const test_buffer = Buffer.from(new ArrayBuffer(50), 40, 10);
console.info(test_buffer.buffer.byteLength); // 50; the size of the memory.
console.info(test_buffer.length); // 10; the size of the view.
Alasan # 2: FastBufferalokasi memori.
Ini mengalokasikan memori dalam dua cara berbeda tergantung pada ukurannya.
- Jika ukurannya kurang dari setengah ukuran kolam memori dan bukan 0 ("kecil") : itu menggunakan kolam memori untuk menyiapkan memori yang diperlukan.
- Lain : itu menciptakan dedicated
ArrayBufferyang persis sesuai dengan memori yang diperlukan.
📜 Node.js 9.4.0/lib/buffer.js#L306-L320
function allocate(size) {
if (size <= 0) {
return new FastBuffer();
}
if (size < (Buffer.poolSize >>> 1)) {
if (size > (poolSize - poolOffset))
createPool();
var b = new FastBuffer(allocPool, poolOffset, size);
poolOffset += size;
alignPool();
return b;
} else {
return createUnsafeBuffer(size);
}
}
📜 Node.js 9.4.0/lib/buffer.js#L98-L100
function createUnsafeBuffer(size) {
return new FastBuffer(createUnsafeArrayBuffer(size));
}
Apa yang Anda maksud dengan " kumpulan memori ?"
Kumpulan memori adalah blok memori pra-alokasi ukuran tetap untuk menjaga potongan memori berukuran kecil untuk Buffers. Menggunakannya membuat potongan memori ukuran kecil tetap rapat, sehingga mencegah fragmentasi yang disebabkan oleh manajemen yang terpisah (alokasi dan deallokasi) dari potongan memori ukuran kecil.
Dalam kasus ini, kumpulan memori adalah ArrayBuffers yang ukurannya 8 KiB secara default, yang ditentukan dalam Buffer.poolSize. Ketika akan menyediakan potongan memori ukuran kecil untuk a Buffer, itu memeriksa apakah kumpulan memori terakhir memiliki cukup memori yang tersedia untuk menangani ini; jika demikian, itu menciptakan Bufferyang “dilihat” potongan parsial diberikan dari kolam memori, jika tidak, itu menciptakan kolam memori baru dan sebagainya.
Anda dapat mengakses dasar ArrayBufferdari a Buffer. The Buffer's bufferproperti (yaitu, diwarisi dari Uint8Array) memegang itu. Sebuah “kecil” Buffer 's bufferproperti merupakan ArrayBufferyang mewakili seluruh kolam memori. Jadi dalam hal ini, ArrayBufferdan Bufferukurannya bervariasi.
const zero_sized_buffer = Buffer.allocUnsafe(0);
const small_buffer = Buffer.from([0xC0, 0xFF, 0xEE]);
const big_buffer = Buffer.allocUnsafe(Buffer.poolSize >>> 1);
// A `Buffer`'s `length` property holds the size, in octets, of the view.
// An `ArrayBuffer`'s `byteLength` property holds the size, in octets, of its data.
console.info(zero_sized_buffer.length); /// 0; the view's size.
console.info(zero_sized_buffer.buffer.byteLength); /// 0; the memory..'s size.
console.info(Buffer.poolSize); /// 8192; a memory pool's size.
console.info(small_buffer.length); /// 3; the view's size.
console.info(small_buffer.buffer.byteLength); /// 8192; the memory pool's size.
console.info(Buffer.poolSize); /// 8192; a memory pool's size.
console.info(big_buffer.length); /// 4096; the view's size.
console.info(big_buffer.buffer.byteLength); /// 4096; the memory's size.
console.info(Buffer.poolSize); /// 8192; a memory pool's size.
3. Jadi kita perlu mengekstrak memori itu " dilihat ."
Sebuah ArrayBufferadalah tetap dalam ukuran, sehingga kita perlu untuk mengambil keluar dengan membuat salinan bagian. Untuk melakukan hal ini, kita menggunakan Buffer's byteOffsetproperti dan lengthproperti , yang diwarisi dari Uint8Array, dan yang ArrayBuffer.prototype.slicemetode , yang membuat salinan bagian dari ArrayBuffer. The slice()Metode -ing disini terinspirasi oleh @ZachB .
const test_buffer = Buffer.from(new ArrayBuffer(10));
const zero_sized_buffer = Buffer.allocUnsafe(0);
const small_buffer = Buffer.from([0xC0, 0xFF, 0xEE]);
const big_buffer = Buffer.allocUnsafe(Buffer.poolSize >>> 1);
function extract_arraybuffer(buf)
{
// You may use the `byteLength` property instead of the `length` one.
return buf.buffer.slice(buf.byteOffset, buf.byteOffset + buf.length);
}
// A copy -
const test_arraybuffer = extract_arraybuffer(test_buffer); // of the memory.
const zero_sized_arraybuffer = extract_arraybuffer(zero_sized_buffer); // of the... void.
const small_arraybuffer = extract_arraybuffer(small_buffer); // of the part of the memory.
const big_arraybuffer = extract_arraybuffer(big_buffer); // of the memory.
console.info(test_arraybuffer.byteLength); // 10
console.info(zero_sized_arraybuffer.byteLength); // 0
console.info(small_arraybuffer.byteLength); // 3
console.info(big_arraybuffer.byteLength); // 4096
4. Peningkatan kinerja
Jika Anda menggunakan hasil sebagai hanya-baca, atau apa-apa untuk mengubah masukan Buffers'isi , Anda dapat menghindari yang tidak perlu menyalin memori.
const test_buffer = Buffer.from(new ArrayBuffer(10));
const zero_sized_buffer = Buffer.allocUnsafe(0);
const small_buffer = Buffer.from([0xC0, 0xFF, 0xEE]);
const big_buffer = Buffer.allocUnsafe(Buffer.poolSize >>> 1);
function obtain_arraybuffer(buf)
{
if(buf.length === buf.buffer.byteLength)
{
return buf.buffer;
} // else:
// You may use the `byteLength` property instead of the `length` one.
return buf.subarray(0, buf.length);
}
// Its underlying `ArrayBuffer`.
const test_arraybuffer = obtain_arraybuffer(test_buffer);
// Just a zero-sized `ArrayBuffer`.
const zero_sized_arraybuffer = obtain_arraybuffer(zero_sized_buffer);
// A copy of the part of the memory.
const small_arraybuffer = obtain_arraybuffer(small_buffer);
// Its underlying `ArrayBuffer`.
const big_arraybuffer = obtain_arraybuffer(big_buffer);
console.info(test_arraybuffer.byteLength); // 10
console.info(zero_sized_arraybuffer.byteLength); // 0
console.info(small_arraybuffer.byteLength); // 3
console.info(big_arraybuffer.byteLength); // 4096