2

Python サーバーから websocket 経由でバイナリ データを送信します。

data = struct.pack('!BI', 2, 1)
channel.send(channel.BINARY, data)

データ送信は問題なく動作します。クライアント側では、JavaScript は次のように取得します。

onbinarydata: function(data) {
    alert(data.byteLength);
    >> 5
    var array = new Uint8Array(data,0,1);
    alert(array[0]);
    >> 2
    var array2 = new Uint32Array(data,1,5);
    >> Uncaught Error: INDEX_SIZE_ERR: DOM Exception 1
    alert(array2[0]);

これはどのように起こりますか?バイト長からバイト オフセットを差し引いた値は 4 で、BYTY_ELEMENT_SIZE も 4 です。最初の値は問題なく読み込まれますが、次の値は型に関係なく常にエラーになります。このようにバイトオフセットを設定するだけでも

var array2 = new Uint32Array(data,1);

エラーがあります。

4

1 に答える 1

0

4 で割り切れないオフセットを持つ int32/uint32 配列を作成することはできません。int16/uint16 および 2 についても同様です。

これは、CPU アーキテクチャの制限です。

これらの 2 つの変数を とA:Uint16としB:Uint8ます。さまざまな方法でそれらをバイトにマップできます。

  • BBAA(値 B を Uint16 に入れる)
  • 0BAA/ B0AA(アラインメントのために 1 バイトをスキップ)
  • AAB(整列のために並べ替えます)。

ビッグエンディアド/リトルエンディアド、並べ替えなどについて考えたくない場合...つまり、BAA何らかの理由で変数をバイトに入れたい場合は、次のアイデアを使用してください。

アラインされていない変数ごとに、対応するサイズのバッファーに入れ、バイト単位でコピーします。ミスアラインが 2 バイトの場合、コピーはバイトのペアで作成される可能性があります。

var array = new Uint8Array(data,0,1);
alert(array);

var array2 = new Uint8Array(data,1,5);
var abuf2 = new ArrayBuffer(4);
var abuf2_8 = new Uint8Array(abuf2);
// using `subarray` won't help, cause it doesn't create a copy like `slice`
// and the same data will have the same inconsistent memory alignment
for (var i = 0; i < 4; i++) abuf2_8[i] = array2[i];
var abuf2_32 = new Uint32Array(abuf2);
alert(abuf2_32[0]);

ところで、js でパック/アンパックするための準備が整ったコードがいくつかあります。

これはphpパックに似ています

私のコードはあなたにとってもっと興味深いかもしれません.バイナリ文字列にパックするクラスと配列バッファにパックするクラスの2つがあるからです.

于 2012-04-07T09:53:55.903 に答える