Javascript结合了ArrayBuffer部分

时间:2016-09-15 02:39:32

标签: javascript typed-arrays typedarray uint8array

我需要将2个现有的arrayBuffers的2个部分组合成一个新部分。

我正在构建一个解析器,数据来自随机大小的数组缓冲区,数据将溢出到一个的末尾,进入另一个的开头。所以我需要创建一个新的输出缓冲区并复制到一个缓冲区的一部分和另一个缓冲区的开头的一部分。输出只是一个Arraybuffer。

从这个演示开始,我打算使用一些偏移来制作Uint8Arrays然后使用set,问题是某些组合抛出Invalid typed array length。我事先不会知道每个阵列或偏移的长度。

var buffer1 = new ArrayBuffer(8);
var buffer2 = new ArrayBuffer(8);
var buffer3 = new ArrayBuffer(8);

var uint8_1 = new Uint8Array(buffer1);
var uint8_2 = new Uint8Array(buffer2);
var uint8_3 = new Uint8Array(buffer3);

uint8_1.fill(1);
uint8_2.fill(2);

var uint8_1_slice = new Uint8Array(buffer1 , 0 , 3);
var uint8_2_slice = new Uint8Array(buffer2 , 4, 7);

对于这个演示,需要将buffer3设为1,1,1,1,2,2,2,2。

  

无法使用切片

2 个答案:

答案 0 :(得分:1)

  

对于这个演示,需要将buffer3设为1,1,1,1,2,2,2,2。

您可以使用for循环,如果变量uint8_3小于uint8_1,则将n设置为uint8_1.byteLength / 2,否则将uint8_3设置为值在uint8_2

var len = 8;

var buffer1 = new ArrayBuffer(len);
var buffer2 = new ArrayBuffer(len);
var buffer3 = new ArrayBuffer(len);

var uint8_1 = new Uint8Array(buffer1);
var uint8_2 = new Uint8Array(buffer2);
var uint8_3 = new Uint8Array(buffer3);

uint8_1.fill(1);
uint8_2.fill(2);
// `len` : uint8_1.byteLength / 2 + uint8_2.byteLength / 2
for (var n = 0; n < len; n++) {
  uint8_3[n] = n < len / 2 ? uint8_1[n] : uint8_2[n];
}

console.log(uint8_3);

答案 1 :(得分:0)

我看到有些人只使用array.length。只要数组每个元素只有1个字节,它就没问题。如果填充其他类型的数组也很好,但在此示例中a2不是。这就是为什么使用byteLength更好的原因这也是Blob构造函数连接各部分的原因。

// Concatenate a mix of typed arrays
function concatenate(...arrays) {
  // Calculate byteSize from all arrays
  let size = arrays.reduce((a,b) => a + b.byteLength, 0)
  // Allcolate a new buffer
  let result = new Uint8Array(size)

  // Build the new array
  let offset = 0
  for (let arr of arrays) {
    result.set(arr, offset)
    offset += arr.byteLength
  }

  return result
}

// the total length of 1-3 = 5
// the total byteLength of 1-3 = 6
let a1 = Uint8Array.of(1, 2) // [1, 2]
let a2 = Uint16Array.of(3) // [3] just for the fun of it 16 takes up 2 bytes
let a3 = Uint8Array.of(4, 5) // [4, 5]

concatenate(a1, a2, a3) // [1, 2, 3, 0, 4, 5]

/********/
var blob = new Blob([a1, a2, a3])
var res = new Response(blob)
res.arrayBuffer().then(buffer => console.log(new Uint8Array(buffer)))
// [1, 2, 3, 0, 4, 5]