题目:338. 比特位计数
给你一个整数
n
,对于0 <= i <= n
中的每个i
,计算其二进制表示中1
的个数 ,返回一个长度为n + 1
的数组ans
作为答案。
解题思路
根据题目,依次将数据转为二进制,计算每个二进制的1的个数,再依次存入是数组并返回。( Brian Kernighan 算法 )
解题过程
这里利用了 Brian Kernighan 算法 ,Brian Kernighan 算法 是计算一个整数的二进制表示中1的数量(即汉明重量)的有效算法。这个算法的关键在于:
x &= (x - 1)
:这个操作可以将x
的二进制表示中最右边的1变为0。- 重复执行上述操作,直至 x 变为0 ,统计重复次数,即 x 中的1的个数。
class Solution {
public int countOccur(int i) {
int count =0 ;
while (i>0) {
i=i & (i-1);
count++;
}
return count;
}
public int[] countBits(int n) {
int[] ans = new int[n + 1];
for (int i = 0; i < n + 1; i++) {
ans[i] = countOccur(i);
}
return ans;
}
}
动态规划:
class Solution {
public int[] countBits(int n) {
int[] bits = new int[n + 1];
int highBit = 0;
for (int i = 1; i <= n; i++) {
if ((i & (i - 1)) == 0) {
highBit = i;
}
bits[i] = bits[i - highBit] + 1;
}
return bits;
}
}