不工作的负输入的无符号右移功能 [英] Unsigned right shift function not working for negative input

查看:184
本文介绍了不工作的负输入的无符号右移功能的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在寻找一种方式来使用>>> 在PHP 5.5.14的64位版本的JavaScript函数。我发现此功能在我的谷歌搜索:

I'm looking for a way to use the >>> function from JavaScript in the 64-bit version of PHP 5.5.14. I found this function in my googling:

function uRShift($a, $b) 
{ 
    $z = hexdec(80000000); 
    if ($z & $a) 
    { 
        $a = ($a >> 1); 
        $a &= (~$z); 
        $a |= 0x40000000; 
        $a = ($a >> ($b - 1)); 
    } else { 
        $a = ($a >> $b); 
    } 
    return $a; 
}

这个功能似乎正数做工精细,但传递负数时,我得到不同的结果。

This function seems to work fine for positive numbers, but I get differing results when passing in negative numbers.

例如:

PHP:

In: echo uRShift(-672461345, 25);
Out: -149

JavaScript的(铬35):

JavaScript (Chrome 35):

In: -672461345 >>> 25
Out: 107

编辑:

我也试过在上文中提及的答案其它功能。

I also tried the other function mentioned in the answer linked above.

function uRShift($a, $b)
{
    if($b == 0) return $a;
    return ($a >> $b) & ~(1<<(8*PHP_INT_SIZE-1)>>($b-1));
}

PHP:

In: echo uRShift(-672461345, 25);
Out: 549755813867

Runnable接口

推荐答案

为0x80000000 (它写成一个呼叫 hexdec 并存储在 $ Z而言变量在这个例子中)再presents最低的补全负整数( 100000 .. .. 二进制)。这位前pression 〜$ Z而言应该给按位非如此,即最高签署的正整数(这最终被 2147483647 )。

The constant 0x80000000 (it's written as a call to hexdec and stored in the $z variable in this example) represents the lowest signed two's complement negative integer (100000.... in binary). The expression ~$z should give the bitwise NOT of this, namely, the highest signed positive integer (which ends up being 2147483647).

原来的号码( 为0x80000000 ,即 2147483648 )不能存储为签署 32位整数,因此通常将它保存为浮动某​​种。不幸的是,PHP 5.5认为〜(2147483648)等于 -2147483649 ,其中是,如果正确我们处理如: 64位整数

The original number (positive 0x80000000, that is, 2147483648) cannot be stored as a signed 32-bit integer, so normally it would be stored as a float of some kind. Unfortunately, PHP 5.5 thinks that ~(2147483648) is equal to -2147483649, which would be correct if we were dealing with e.g. 64-bit integers.

事实上,呼应了 PHP_INT_SIZE 在可运行表明整数是8个字节,这是64位。因此,运算不正确的在PHP 5.5的工作了。

And indeed, echoing out PHP_INT_SIZE in runnable indicates that integers are 8 bytes, which is 64 bits. Thus, the arithmetic isn't working out right in PHP 5.5.

要解决这个问题,只需更换〜$ Z而言用静态常量,如下所示:

To remedy this, just replace the ~$z with a static constant, as follows:

function uRShift($a, $b) 
{ 
    if ($a < 0) 
    { 
        $a = ($a >> 1); 
        $a &= 2147483647; 
        $a |= 0x40000000; 
        $a = ($a >> ($b - 1)); 
    } else { 
        $a = ($a >> $b); 
    } 
    return $a; 
}

这功能还是有一定的弱点;例如,通过移0不能正常工作。

This function still has some weaknesses; for example, shifting by 0 doesn't work properly.

这篇关于不工作的负输入的无符号右移功能的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆