0

我在我的 socket.io 客户端上获得了很多数据,这些数据可能是也可能不是完整的数据,也可能是大数据,所以我需要让它变得高效。因此,我尝试创建缓冲区并将其解析到我的应用程序中。我知道有一些流/缓冲模块可用,如果它们实现了更高效的目标,我可能会考虑使用它们。期待看到您的答案以及关于如何最好地做到这一点的可能论点。

请注意,与客户端 Javascript 将数据呈现为浏览器友好格式的速度相比,带宽不是我关心的问题。

这是我到目前为止所得到的。

function extended_split(str, separator, max) {
        var out = [],
                index = 0,
                next;

        while (!max || out.length < max - 1 ) {
                next = str.indexOf(separator, index);
                if (next === -1) {
                        break;
                }
                out.push(str.substring(index, next));
                index = next + separator.length;
        }
        out.push(str.substring(index));
        return out;
};  

var buffer = ''; 

// data format "\nOP:ARGS:DATA(could be base64 or 'other' depending on OP)\0";
socket.on('ioSend', function(data) {
    data = String.fromCharCode.apply(null, new Uint16Array(data));
    buffer = buffer + data; 
    while(buffer.indexOf('\n') != -1 && extended_split(buffer, '\n', 2)[1].indexOf('\0') != -1)
    {
        splitted = extended_split(extended_split(buffer, '\n', 2)[1], '\0', 2);  
        parse = splitted[0];
        buffer = splitted[1];  
        parse = parse.split(':');
        // Do stuff with parse here                     
    } 
});
4

2 回答 2

1

滚动您自己的缓冲区构建器/解析器是可以的,但是您可以花费双倍的时间来工作和维护它,而不仅仅是获得一个生产就绪的脚本。

现在从我的角度来看,我首先会socket.io考虑您的情况,因为it just doesn't transmit binary as it should还有其他模块可以传输二进制https://github.com/binaryjs/binaryjs,它们更适合通过 websocket 协议进行二进制传输。

我还会尝试http://bsonspec.org/ (检查节点模块的实现),它将您的 json 编码为二进制文件,这样您就可以跳过构建和维护缓冲区解析器/构建器的整个问题。

于 2013-11-07T13:25:18.257 回答
0

我对此进行了另一次破解,并放弃了扩展拆分的想法并提出了这个。

socket.on('ioSend', function(data) {                                    // receive command from socket.io
    if (safeBrowser) {                                                  // IE < 10 doesn't support Uint16Array
        var xdata = new Uint16Array(data);
        data = String.fromCharCode.apply(null, xdata);
        buffer = buffer + data;                                         // Update the buffer with most recent ioSend data  
    }
    else {                                                              // So we have to kludge this in for IE < 10 
        var xdata = '';
        for (var i = 0; i < data.length; i++) {
            xdata += String.fromCharCode(data[i]);
        }
        buffer = buffer + xdata;                                         // Update the buffer with most recent ioSend data   
    }
    var splitA = [];
    var splitB = [];
    while(buffer.indexOf(d1) != -1 && buffer.indexOf(d2) != -1)         // While loop reads buffer until there are no commands left to issue
    {
        splitA = buffer.split(d2);                  // Array with rear delimiter
        splitB = splitA[0].split(d1);           
        doParse.call(null, splitB[1]);              // This should be an @command
        splitB = null;
        splitA.shift();                             // Shift array
        buffer = splitA.join(d2);                   // Update buffer from shifted array with rear delimiter
    }     
});

它在我所有的单元测试中都非常快,并且做得非常好。我正在开发一个不使用@GeoPhoenix 建议的socket.io 的实现,但在此之前效果很好。

于 2013-12-13T17:55:58.467 回答