【问题标题】:Computing the absolute value of an n-bit 2's complement number计算 n 位 2 的补数的绝对值
【发布时间】:2013-01-20 05:49:10
【问题描述】:

该方法接受一个 n 位 2 的补数,我们试图找到其绝对值,以及该数字的位数。下面是一些例子:

abs(0x00001234, 16); // => 0x00001234

abs(0x00001234, 13); // => 0x00000DCC

所以你可以看到,在第一个例子中,0x00001234 只是产生了自己,因为它有 16 位,它有足够的前导零来成为它自己。

但是,对于第二个示例,使用 13 位会使 0x00001234 的符号位为 1,因此当您将此 13 位数字转换为正数时,它会产生 0x00000DCC。

我觉得到目前为止我所拥有的应该可以工作,但在某些情况下它不起作用:/ 知道出了什么问题或我应该往哪个方向前进吗?

编辑:另外忘了提一下,我们不能使用 >>> 或 +,-,*,/ 除非我们只是增加 1。

public static int abs(int num, int n)
{

    boolean set = ((1 << n-1) & num) == (1 << n-1);
    if (!set) {
        return num;
    } else {
        int bitmask = (0x7FFFFFFF >> (32-n)) | (1 << n-1);
        return (num ^ bitmask) + 1;
    }
}

【问题讨论】:

  • 给出一些失败的案例...
  • 每当 n 变量截止使 num 变量在 2 的补码中为负时,它就会失败。所以例如 abs(0x00001234, 13) 失败

标签: java bit-manipulation twos-complement absolute-value


【解决方案1】:

哇,以后来的人请看:

  public static int abs(int num, int n)
  {
      int topbit = 1<<(n-1);
      int ones = (topbit<<1)-1;
      num &= ones;                     // sanity check
      if (0==(topbit&num)) {
          return num;
      } else {
          return (num ^ ones) + 1;
      }
  }

所以问题是,可以从这里删除操作以使此功能更快吗?

【讨论】:

    【解决方案2】:

    这是错误的

    int bitmask = 0xFFFFFFFF >> (32 - n);
    

    它总是0xFFFFFFFF,使用

    int bitmask = 0xFFFFFFFF >>> (32 - n);
    

    http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.19

    UPDATE 正如我从您的评论中了解到的那样,您不允许使用无符号移位。在这种情况下尝试

        int bitmask = (int) (0xFFFFFFFFL >> (32 - n));
    

    完整代码

    public static int abs(int num, int n) {
        int bitmask = (int) (0xFFFFFFFFL >> (32 - n));
        boolean set = ((1 << n - 1) & num) != 0;
        if (!set) {
            return num & bitmask;
        } else {
            return -(num | ~bitmask);
        }
    }
    

    【讨论】:

    • 这行得通,但我们实际上是不允许使用它的……对不起,我之前没有提到过。有什么办法吗?
    • 是的,使用 (0x7FFFFFFF >> (32-n)) |(1
    • 也可以,但我仍然不知道如何在 32- n 左右工作,因为我们不能使用减法:/
    • 应该检查,但我认为 (0x7FFFFFFF >> (32-n)) |(1 相同
    • 他不能使用 / :p 这就像试图蒙着眼睛吃晚餐。
    猜你喜欢
    • 1970-01-01
    • 2021-09-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-08-16
    • 1970-01-01
    相关资源
    最近更新 更多