转换具有2x32位单元< - >数单元、GT、LT

2023-09-08 15:01:20 作者:触碰岁月

一个人怎么会从2x32bit uints转换为数字和背面(假设2 ^ 52最大值)?

How would one convert from 2x32bit uints to a Number and back (assume max value of 2^52)?

我相信下面的理论上的工作(绕过作为ByteArray中的清晰度,但数组可以作为存储以及工作),但它并没有因为按位运算符显然迫使数为32位:\

I believe the following would theoretically work (passing around as ByteArray for clarity, but an Array could work as storage as well), But it doesn't because bitwise operators evidently force Number into 32 bits :\

(参见:Binary数学上的对象数量限制为32位):

public static function read64BitNumberFromBuffer(buffer:ByteArray):Number {
    var ch1:uint = buffer.readUnsignedInt();
    var ch2:uint = buffer.readUnsignedInt();
    var num:Number = ((ch1 << 32) | ch2);

    return(num);
}

public static function write64BitNumberToBuffer(num:Number):ByteArray {
    var ch1:uint = uint((num & 0xFFFFFFFF00000000) >> 32);
    var ch2:uint = uint(num  & 0xFFFFFFFF);
    var buffer:ByteArray = new ByteArray();

    buffer.writeUnsignedInt(ch1);
    buffer.writeUnsignedInt(ch2);

    return(buffer);
}

人们可以使用类似as3crypto的BigInteger的库来处理这个问题,但是,似乎是一个可怕的很多膨胀的这样一个离散的需求。是否有code进行健壮位可能被注入到上述功能,使它们返回正确的值?

One could use a library like as3crypto's BigInteger to handle this, but that seems like an awful lot of bloat for such a discrete need. Is there a robust bit of code that could be injected into the above functions to make them return the correct values?

虽然我preFER一个纯ActionScript的解决方案,作为一个点兴趣而被逐位运营商在横桥也仅限于32位? (btw-我需要1500声誉创建一个标签横桥,有人可以做到这代表我?)

Although I'd prefer a pure Actionscript solution, as a point of interest- are bitwise operators in Crossbridge also limited to 32 bits? (btw- I need 1500 reputation to create a tag "crossbridge", can someone do it on my behalf?)

编辑:试过readDouble()/ writeDouble()作为很好,但它似乎想要切换到反转下一个更详尽的测试(试图与端设置玩字节出于某种原因,没有果除了它没有影响到错误的方式输出)

Tried readDouble()/writeDouble() as well but it seemed to want to switch to reverse the bytes for some reason under a more thorough test (tried playing with endian setting, to no avail other than it did affect output in the wrong way)

推荐答案

确定 - 这似乎是完美的工作:

OK- this seems to work perfectly:

package
{
    import flash.display.Sprite;
    import flash.utils.ByteArray;

    public class TEMP extends Sprite
    {
        public function TEMP()
        {
            var targetNumber:Number = 6697992365;
            var buffer:ByteArray = new ByteArray();
            var testNumber:Number; 

            write64BitNumberToBuffer(buffer, targetNumber);

            buffer.position = 0;
            testNumber = read64BitNumberFromBuffer(buffer);

            if(targetNumber == testNumber) {
                trace("Passed! Both numbers are", targetNumber);
            } else {
                trace("Failed! Test number is", testNumber, "When it should be", targetNumber);
            }

        }

        public static function read64BitNumberFromBuffer(buffer:ByteArray):Number {
            var finalNumber:Number;
            var str:String = '';
            var byte:uint;
            var chr:String;

            while(str.length < 16) {
                byte = buffer.readUnsignedByte();
                chr = byte.toString(16);
                if(chr.length == 1) {
                    chr = '0' + chr;
                }
                str += chr;
            }

            finalNumber = Number('0x' + str);

            return(finalNumber);
        }

        public static function write64BitNumberToBuffer(buffer:ByteArray, num:Number) {
            var hexString:String = num.toString(16);
            var idx:uint = 16 - hexString.length;
            var byte:uint;

            while(idx--) {
                hexString = '0' + hexString;
            }

            for(idx = 0; idx < hexString.length; idx += 2) {
                byte = uint('0x' + hexString.substr(idx, 2));
                buffer.writeByte(byte);
            }
        }
    }
}

输出:过去了!这两个数字都6697992365

Output: Passed! Both numbers are 6697992365