将项目推送到数组中的最佳性能方式?

Raz*_*a O 8 javascript arrays multithreading web-worker typed-arrays

在我的网站上,我有很多数据阵列.例如:顶点数组,颜色数组,大小数组...

我正在处理大量物品.高达数千万.

在将数据添加到数组之前,我需要处理它.到现在为止,我在主线程中做到了这一点,这让我的网站冻结了X秒.它因处理而冻结,并且因为将处理后的数据添加到数组中.

今天我'把'(做了很多工作)处理成了web worker,但处理后的数据正在主线程中添加.我设法节省了处理的冻结时间,但没有添加.

添加只需通过array.push()或完成array.splice().

我已经阅读了一些关于数组是如何工作的文章,并且发现当我们将项添加到数组时,数组被完全复制到内存中具有array.length + 1大小的新位置并且添加了值.这使我的数据推迟.

我还读到类型数组要快得多.但为此,我需要知道数组的大小,我不知道,并且创建一个带有额外计数器的大型数组,并在中间(而不是数组的末尾)管理添加项目将是一个很多代码改变,我现在不想做.

所以,对于我的问题,我有从Web工作者返回的TypedArray,我需要将其放入常规数组中.什么是最好的方法来做到这一点?(今天我在一个循环中跑,一个接一个地推)

编辑

网站工作原理示例:客户端添加项目数,例如100000.正在收集项目原始数据并发送给工作人员.工作人员正在处理所有信息并将处理后的数据作为类型数组发回(用作可转移对象).在主线程中,我们将处理后的数据添加到数组 - 最后或某些特定索引中.第二轮.客户端添加另外100000个项目.发送给worker并将结果添加到主线程数组中.第3轮可以是10项,第4轮10000,第5轮可以删除指数10-2000,...

Raz*_*a O 5

做了一些更多的研究使用评论和思考另一个方向.

我尝试过使用typedArray.set方法并发现它非常快.

使用套装的1000万件物品耗时0.004秒,相比之下array.push0.866秒.我将10百万个数据分成10个数组,以确保从索引0开始时set方法的工作速度不快.

通过这种方式,我认为我甚至可以insertAtIndex使用TypedArray来实现我自己的,它将所有项目向前推,并在正确的索引中设置新的项目.

另外,我可以TypedArray.subArray根据数组中的实际数据量(不复制数据)来获取子数据 - 用于将数据上传到缓冲区(WebGL)

我说我想使用常规阵列,但这种性能提升我不认为我会得到其他明智的.它是不是这么多的工作,当我包装MyNewTypedArray作为TypedArray所有的push,splice,自己的实现.

希望这些信息能帮到任何人

var maxCount = 10000000;
var a = new Float32Array(maxCount);
var aSimple = [];

var arrays = [];
var div = 10;
var arrayLen = maxCount / div;
for (var arraysIdx = 0; arraysIdx < div; arraysIdx++) {
  var b = new Float32Array(arrayLen);
  for (var i = 0; i < b.length; i++) {
    b[i] = i * (arraysIdx + 1);
  }
  arrays.push(b);
}

var timeBefore = new Date().getTime();

for (var currArrayIdx = 0; currArrayIdx < arrays.length; currArrayIdx++) {
  a.set(arrays[currArrayIdx], currArrayIdx * arrayLen);
}
var timeAfter = new Date().getTime();
good.innerHTML = (timeAfter - timeBefore) / 1000 + " sec.\n";
timeBefore = new Date().getTime();
for (var currArrayIdx = 0; currArrayIdx < arrays.length; currArrayIdx++) {
  for (var i = 0; i < arrayLen; i++) {
    aSimple.push(arrays[currArrayIdx][i]);
  }
}

timeAfter = new Date().getTime();
bad.innerHTML = (timeAfter - timeBefore) / 1000 + " sec.\n";
Run Code Online (Sandbox Code Playgroud)
Using set of TypedArray:
<div id='good' style='background-color:lightGreen'>working...</div>
Using push of Array:
<div id='bad' style='background-color:red'>working...</div>
Run Code Online (Sandbox Code Playgroud)