位运算 | 豆包MarsCode AI刷题

45 阅读2分钟

题目内容:

小C在学习二进制运算,他了解到每个非负整数都有其二进制表示。例如,整数 5 可以被表示为二进制 "101",整数 11 可以被表示为二进制 "1011",并且除了 N = 0 外,任何二进制表示中都不含前导零。

二进制的反码表示是将每个 1 变为 0,每个 0 变为 1。例如,二进制数 "101" 的二进制反码为 "010"。现在小C想知道,给定一个十进制数 N,它的二进制反码对应的十进制数是多少。


测试样例

样例1:

输入:N = 5
输出:2

解题代码如下:

public static int solution(int N) {
    if (N == 0) return 1;
    int length = 0;
    for (int i = N; i > 0; i /= 2) {
        length++;
    }
    int allOnesValue = (1 << length) - 1;
    return allOnesValue ^ N;
    }

对位运算了解不多,去查了相关资料。

位运算就是直接对整数在内存中的二进制位进行操作。

常见的运算符有与(&)、或(|)、异或(^)、取反(~)、左移(<<)、右移(>>是带符号右移 >>>无符号右移动)。

位运算 & (与)

规则:二进制对应位两两进行逻辑AND运算(只有对应位的值都是 1 时结果才为 1, 否则即为 0)即 0&0=0, 0&1=0, 1&1=1,两者都为1即为真。

位运算 | (或)

规则:二进制对应位两两进行逻辑或运算(对应位中有一 个为1则为1) 即0|0=0,0|1=1,1|1=1,只要有1就是真。

位运算 ^ (异或)

规则:二进制对应位两两进行逻辑XOR (异或) 的运算(当对应位的值不同时为 1, 否则为 0)即0^0=00^1=11^1=0 两者值不同即为真。

按位取反~

规则:二进制的0变成1,1变成0。 两者取不同的值。

移位运算符

扩大 左移运算<<:左移后右边位补 0

缩小 右移运算>>:右移后左边位补原最左位值(可能是0,可能是1)

右移运算>>>:右移后左边位补 0

  • 对于左移运算符<<没有悬念右侧填个零无论正负数相当于整个数乘以2。
  • 而右移运算符就有分歧了,分别是左侧补0>>>和左侧补原始位>>,如果是正数没争议左侧都是补0,达到除以2的效果;如果是负数的话左侧补0>>>那么数值的正负会发生改变,会从一个负数变成一个相对较大的正数。而如果是左侧补原始位(负数补1)>>那么整个数还是负数,也就是相当于除以2的效果。

image.png

查阅资料学习对位运算的了解多了一些。