1. 程式人生 > 實用技巧 >js 位元組陣列轉數字以及數字轉位元組陣列

js 位元組陣列轉數字以及數字轉位元組陣列

javascript通過ArrayBuffer和DataView實現位元組陣列和數字之間的相互轉換

注意!我這裡的所有函式用的都是大端位元組序(高位在前,低位在後),即資料的高位元組,儲存在記憶體的低地址中,而資料的低位元組,儲存在記憶體的高地址中

舉例:2個位元組的無符號整型1的二進位制表示

大端模式: 0000 0000 0000 0001

小端模式: 0000 0001 0000 0000

如果位元組序不一致,解析的資料就會出錯!如果你的資料是小端模式,就需要翻轉陣列,或者重寫這些函式,DataView的setInt32和getInt32之類的函式可以傳入一個引數來控制大端還是小端,我採用的是預設的情況下的大端模式

具體程式碼如下

    test();
    
function test() { var bytes = getFloat64Bytes(-3.33); alert(bytes); alert(toFloat64(bytes)); } //構建一個檢視,把位元組陣列寫到快取中,索引從0開始,大端位元組序 function getView(bytes) { var view = new DataView(new ArrayBuffer(bytes.length)); for (var i = 0; i < bytes.length; i++) { view.setUint8(i, bytes[i]); }
return view; } //將位元組陣列轉成有符號的8位整型,大端位元組序 function toInt8(bytes) { return getView(bytes).getInt8(); } //將位元組陣列轉成無符號的8位整型,大端位元組序 function toUint8(bytes) { return getView(bytes).getUint8(); } //將位元組陣列轉成有符號的16位整型,大端位元組序 function toInt16(bytes) { return
getView(bytes).getInt16(); } //將位元組陣列轉成無符號的16位整型,大端位元組序 function toUint16(bytes) { return getView(bytes).getUint16(); } //將位元組陣列轉成有符號的32位整型,大端位元組序 function toInt32(bytes) { return getView(bytes).getInt32(); } //將位元組陣列轉成無符號的32位整型,大端位元組序 function toUint32(bytes) { return getView(bytes).getUint32(); } //將位元組陣列轉成32位浮點型,大端位元組序 function toFloat32(bytes) { return getView(bytes).getFloat32(); } //將位元組陣列轉成64位浮點型,大端位元組序 function toFloat64(bytes) { return getView(bytes).getFloat64(); } //將數值寫入到檢視中,獲得其位元組陣列,大端位元組序 function getUint8Array(len, setNum) { var buffer = new ArrayBuffer(len); //指定位元組長度 setNum(new DataView(buffer)); //根據不同的型別呼叫不同的函式來寫入數值 return new Uint8Array(buffer); //建立一個位元組陣列,從快取中拿取資料 } //得到一個8位有符號整型的位元組陣列,大端位元組序 function getInt8Bytes(num) { return getUint8Array(1, function (view) { view.setInt8(0, num); }) } //得到一個8位無符號整型的位元組陣列,大端位元組序 function getUint8Bytes(num) { return getUint8Array(1, function (view) { view.setUint8(0, num); }) } //得到一個16位有符號整型的位元組陣列,大端位元組序 function getInt16Bytes(num) { return getUint8Array(2, function (view) { view.setInt16(0, num); }) } //得到一個16位無符號整型的位元組陣列,大端位元組序 function getUint16Bytes(num) { return getUint8Array(2, function (view) { view.setUint16(0, num); }) } //得到一個32位有符號整型的位元組陣列,大端位元組序 function getInt32Bytes(num) { return getUint8Array(4, function (view) { view.setInt32(0, num); }) } //得到一個32位無符號整型的位元組陣列,大端位元組序 function getUint32Bytes(num) { return getUint8Array(4, function (view) { view.setUint32(0, num); }) } //得到一個32位浮點型的位元組陣列,大端位元組序 function getFloat32Bytes(num) { return getUint8Array(4, function (view) { view.setFloat32(0, num); }) } //得到一個64位浮點型的位元組陣列,大端位元組序 function getFloat64Bytes(num) { return getUint8Array(8, function (view) { view.setFloat64(0, num); }) } ////下面幾個為另一種實現方式的版本,只實現了簡單幾種,其他的實現起來比較麻煩,所以就中途放棄了 //function toInt32(bytes) { // return ((bytes[0] & 0xFF) << 24) | ((bytes[1] & 0xFF) << 16) | ((bytes[2] & 0xFF) << 8) | (bytes[3] & 0xFF); //} //function toUInt16(bytes) { // return ((bytes[0] & 0xFF) << 8) | (bytes[1] & 0xFF); //} //function toInt16(bytes) { // return bytes[0] >> 7 == 0 ? toUInt16(bytes) : toUInt16(bytes) - 65536; //} //function getInt32Bytes(num) { // return [num >> 24 & 0xFF, num >> 16 & 0xFF, num >> 8 & 0xFF, num & 0xFF]; //} //function getUint16Bytes(num) { // return [num >> 8 & 0xFF, num & 0xFF]; //} //function getInt16Bytes(num) { // return num >= 0 ? getUint16Bytes(num) : getUint16Bytes(65536 + num); //}