将 JS 对象转换为 ArrayBuffer 以向/从 Web Worker 传输等于瓶颈

Posted

技术标签:

【中文标题】将 JS 对象转换为 ArrayBuffer 以向/从 Web Worker 传输等于瓶颈【英文标题】:Converting JS object to ArrayBuffer to transfer to/from web worker equals bottleneck 【发布时间】:2017-01-20 16:53:51 【问题描述】:

我有一个网络工作者,它不断地计算大量数据,当完成一轮时,它是一个 js 对象,然后我将其解析为 ArrayBuffer,然后将其发送到主线程。

不能做太多的计算,ArrayBuffer 的传输很快。但是这个对象的解析却减慢了这个过程。由于对象本身包含更多对象的数组。

在 Firefox 中,我收到以下警告:

A script on this page may be busy, or it may have stopped responding.
You can stop the script now, open the script in the debugger,
or let the script continue.

Script: http://localhost/js/util/DataViewSerializer.js:435

第 435 行指的是我序列化数组的函数。该行是声明 for 循环的地方。

DataViewSerializer.prototype.setArray = function (array, serializer) 
    var i,
        l = JSUtil.hasValue(array) ? array.length : 0;

    this.setUint32(l);

    console.log(array, serializer);
    for (i = 0; i < l; i += 1) 
        if (serializer !== undefined) 
            serializer.serializeTo(array[i], this);
         else 
            array[i].serializeTo(this);
        
    
;

我正在阅读有关网络工作者和主线程之间的Transferable Object 的信息。因为发送 ArrayBuffers 似乎是唯一的方法。

所以我的问题是是否有更快的方法将 js 对象转换为 ArrayBuffer?或者有什么其他建议可以加快速度?

【问题讨论】:

你可以使用ArrayBuffer而不是Array,然后你可能只需要转换一次吗? 可能是最后的手段,因为我需要重写很多代码。而且我认为调试或跟踪它会更难。 【参考方案1】:

这个角色的问题已经在网络工作者中被问过 3 次了。这两个是我用很长的答案回答的:

How to transfer large objects using postMessage of webworker? Converting javascript 2d arrays to ArrayBuffer

鉴于我已经写了很多文字,我将重复主题:

除非结构化克隆算法不支持您的数据,否则不要使用自定义序列化来支持结构化克隆算法!

也就是说,只需调用:

worker.postMessage(name: "MY_MESSAGE", data:myArray);

【讨论】:

以上是关于将 JS 对象转换为 ArrayBuffer 以向/从 Web Worker 传输等于瓶颈的主要内容,如果未能解决你的问题,请参考以下文章

ArrayBuffer 转换为字符串

javascript 怎么将字符串转换为ArrayBuffer

使用 POST 表单发送 Blob 对象

javascript 将arraybuffer转换为string,将string转换为arraybuffer

如何在ArrayBuffer对象与字符串之间进行互相转换

哪位朋友使用过js中的ArrayBuffer,请教一个转换问题