将javascript Integer转换为Byte数组并返回

Ben*_*ves 36 javascript

function intFromBytes( x ){
    var val = 0;
    for (var i = 0; i < x.length; ++i) {        
        val += x[i];        
        if (i < x.length-1) {
            val = val << 8;
        }
    }
    return val;
}

function getInt64Bytes( x ){
    var bytes = [];
    var i = 8;
    do {
    bytes[--i] = x & (255);
    x = x>>8;
    } while ( i )
    return bytes;
}
Run Code Online (Sandbox Code Playgroud)

我试图将javascript编号转换为字节数组,然后返回到数字.但是,上述功能会产生非常大数量的错误输出.

var array = getInt64Bytes(23423423);    
var value = intFromBytes(array);

console.log(value); //Prints 23423423 - correct

var array = getInt64Bytes(45035996273704);  
var value = intFromBytes(array);

console.log(value); //Prints -1030792152 - incorrect
Run Code Online (Sandbox Code Playgroud)

据我所知,javascript浮动是53位所以它不应该溢出?警报(Math.pow(2,53))工作正常.

You*_*nes 42

使用Susanoh13提供的提示,这里有两个函数允许从/到ByteArray转换数字:

longToByteArray = function(/*long*/long) {
    // we want to represent the input as a 8-bytes array
    var byteArray = [0, 0, 0, 0, 0, 0, 0, 0];

    for ( var index = 0; index < byteArray.length; index ++ ) {
        var byte = long & 0xff;
        byteArray [ index ] = byte;
        long = (long - byte) / 256 ;
    }

    return byteArray;
};

byteArrayToLong = function(/*byte[]*/byteArray) {
    var value = 0;
    for ( var i = byteArray.length - 1; i >= 0; i--) {
        value = (value * 256) + byteArray[i];
    }

    return value;
};
Run Code Online (Sandbox Code Playgroud)

  • 不要使用此代码。仅当 Javascript 数字是 64 位无符号整数时,此代码才有效。然而它们是 64 位浮点数,最多只能存储 52 位作为精确整数。这意味着虽然此代码适用于许多字节(例如,[0,1,2,3,4,5,6,7]),但当实际使用所有位时,它将失败。一些失败的情况是(转换为数字并再次返回会给出不同的结果): ([255,255,255,255,255,255,255,255] =&gt; [0, 0, 0, 0, 0, 0, 0, 255]), ([1,2, 3,4,5,6,7,8] =&gt; [0, 2, 3, 4, 5, 6, 7, 8]), ([1,0,0,0,0,0,0,1 ] =&gt; [0, 0, 0, 0, 0, 0, 0, 1]) (4认同)
  • 这不适用于负数。取而代之的是对大正数进行解码。 (2认同)

Cro*_*zin 14

在JavaScript中,位移(>>,<<)总是在带符号的32位整数上执行.这导致大量范围溢出.


Kam*_*ski 5

try(**幂运算符<<并且>>>位移运算符) -intFromBytes仅适用于从正整数生成的数组

function getInt64Bytes(x) {
  let y= Math.floor(x/2**32);
  return [y,(y<<8),(y<<16),(y<<24), x,(x<<8),(x<<16),(x<<24)].map(z=> z>>>24)
}

function intFromBytes(byteArr) {
    return byteArr.reduce((a,c,i)=> a+c*2**(56-i*8),0)
}
Run Code Online (Sandbox Code Playgroud)

function getInt64Bytes(x) {
  let y= Math.floor(x/2**32);
  return [y,(y<<8),(y<<16),(y<<24), x,(x<<8),(x<<16),(x<<24)].map(z=> z>>>24)
}

function intFromBytes(byteArr) {
    return byteArr.reduce((a,c,i)=> a+c*2**(56-i*8),0)
}
Run Code Online (Sandbox Code Playgroud)


ast*_*tef 5

2022年,你应该使用Buffer来处理字节,使用BigInt来处理大整数。

所以你的代码可能如下所示:

import { Buffer } from "node:buffer";

/**
 * @param {BigInt} x
 * @returns {Buffer}
 */
function getInt64Bytes(x) {
  const bytes = Buffer.alloc(8);
  bytes.writeBigInt64LE(x);
  return bytes;
}

/**
 * @param {Buffer} x 
 * @returns {BigInt}
 */
function intFromBytes(x) {
  return x.readBigInt64LE();
}

var array = getInt64Bytes(BigInt(23423423));
var value = intFromBytes(array);

console.log(value); // 23423423n

var array = getInt64Bytes(BigInt(45035996273704));
var value = intFromBytes(array);

console.log(value); // 45035996273704n
Run Code Online (Sandbox Code Playgroud)