lizhongzhen11 / lizz-blog

前端学习
80 stars 6 forks source link

重学js —— 结构化数据之ArrayBuffer对象 #122

Open lizhongzhen11 opened 4 years ago

lizhongzhen11 commented 4 years ago

ArrayBuffer 对象

AllocateArrayBuffer ( constructor, byteLength )

用于创建 ArrayBuffer 对象。

  1. 定义 obj? OrdinaryCreateFromConstructor(constructor, "%ArrayBuffer.prototype%", « [[ArrayBufferData]], [[ArrayBufferByteLength]], [[ArrayBufferDetachKey]] »)
  2. 断言:! IsNonNegativeInteger(byteLength) 为 true
  3. 定义 block? CreateByteDataBlock(byteLength) (PS:该方法会将生成的 Data Block 所有字节设置为0)
  4. obj.[[ArrayBufferData]] 设置为 block
  5. obj.[[ArrayBufferByteLength]] 设置为 byteLength
  6. 返回 obj

IsDetachedBuffer ( arrayBuffer )

  1. 断言:arrayBuffer 是对象类型,它拥有 [[ArrayBufferData]] 内置插槽
  2. 如果 arrayBuffer.[[ArrayBufferData]]null,返回 true
  3. 返回 false

还有很多抽象操作,感觉没必要全翻译

ArrayBuffer 构造器

ArrayBuffer ( length )

  1. 如果 NewTargetundefined,抛 TypeError 异常
  2. 定义 byteLength? ToIndex(length)
  3. 返回 ? AllocateArrayBuffer(NewTarget, byteLength)

构造器上的属性

ArrayBuffer.isView ( arg )

ArrayBuffer.isView(new ArrayBuffer(10)); // false
ArrayBuffer.isView(new Uint8Array()); // true
  1. 如果 arg 不是对象,返回 false
  2. 如果 arg[[ViewedArrayBuffer]] 内置插槽,返回 true
  3. 返回 false

ArrayBuffer 原型对象属性

get ArrayBuffer.prototype.byteLength

  1. 定义 Othis
  2. 执行 ? RequireInternalSlot(O, [[ArrayBufferData]])
  3. 如果 OSharedArrayBuffer,抛 TypeError 异常
  4. 如果 IsDetachedBuffer(O) 为 true,抛 TypeError 异常
  5. 定义 lengthO.[[ArrayBufferByteLength]]
  6. 返回 length

ArrayBuffer.prototype.constructor

初始值为 %ArrayBuffer%

ArrayBuffer.prototype.slice ( start, end )

  1. 定义 Othis
  2. 执行 ? RequireInternalSlot(O, [[ArrayBufferData]])
  3. 如果 OSharedArrayBuffer,抛 TypeError 异常
  4. 如果 IsDetachedBuffer(O) 为 true,抛 TypeError 异常
  5. 定义 lenO.[[ArrayBufferByteLength]]
  6. 定义 relativeStart? ToInteger(start)
  7. 如果 relativeStart < 0,定义 firstmax((len + relativeStart), 0);否则,定义 firstmin(relativeStart, len)
  8. 如果 endundefined,定义 relativeEndlen;否则,定义 relativeEnd? ToInteger(end)
  9. 如果 relativeEnd < 0,定义 finalmax((len + relativeEnd), 0);否则,定义 finalmin(relativeEnd, len)
  10. 定义 newLenmax(final - first, 0)
  11. 定义 ctor? SpeciesConstructor(O, %ArrayBuffer%)
  12. 定义 new? Construct(ctor, « newLen »)
  13. 执行 ? RequireInternalSlot(new, [[ArrayBufferData]])
  14. 如果 newSharedArrayBuffer,抛 TypeError 异常
  15. 如果 IsDetachedBuffer(new) 为 true,抛 TypeError 异常
  16. 如果 SameValue(new, O) 为 true,抛 TypeError 异常
  17. 如果 new.[[ArrayBufferByteLength]] < newLen,抛 TypeError 异常
  18. 注意:上述步骤的副作用可能使 O 脱离。
  19. 如果 IsDetachedBuffer(O) 为 true,抛 TypeError 异常
  20. 定义 fromBufO.[[ArrayBufferData]]
  21. 定义 toBufnew.[[ArrayBufferData]]
  22. 执行 CopyDataBlockBytes(toBuf, 0, fromBuf, first, newLen)
  23. 返回 new

ArrayBuffer和Array

这俩不同。 Array 可以动态扩展;ArrayBuffer 表示固定长度的原始二进制数据缓冲区!

使用 new ArrayBuffer(length) 创建指定大小的 ArrayBuffer 对象,但是不能像操作数组一样直接对其操作,几乎任何对 ArrayBuffer 的操作,都需要一个 视图。视图可以是 TypedArray,也可以是 DataView

也就是说想操作 ArrayBuffer,必须先用视图映射下,然后操作视图即可:

let buffer = new ArrayBuffer(16); // 创建一个字节长度为 16 的 buffer
let view = new Uint32Array(buffer); // 将 buffer 视为一个 32 位整数的序列
console.log(view)
// Uint32Array(4) [0, 0, 0, 0]
// 让我们写入一个值
view[0] = 123456;
// Uint32Array(4) [123456, 0, 0, 0]