题目
难度:中等
思路
动态规划
时间复杂度:O(n)
先列出一些数字,观察它们的二进制特点,当数字i:
i为奇数时,1的个数是dp[i-1]+1;
i为偶数时,如果i为2的幂次,dp[i]=1;否则,dp[i]是前面某两个偶数的dp之和。
为解决i为偶数时的判断,此处设置两个指针low,high,刚开始都指向2。
如果low==high,证明数字i是2的幂次,dp[i]=1,重置low=2,前移high=i;
如果low!=high,dp[i]=dp[low]+dp[high],low+=2。
C++代码
class Solution {
public:
vector<int> countBits(int num) {
if (num == 0)return{ 0 };
if (num == 1)return { 0,1 };
if (num == 2)return{ 0,1,1 };
vector<int>dp(num + 1, 0);
dp[0] = 0; dp[1] = 1; dp[2] = 1;
int low = 2, high = 2,i=3;
while (i <= num) {
if (i & 1)dp[i] = dp[i - 1] + 1;//奇数
else { //偶数
if (low == high) { //2的幂次
dp[i] = 1;
low = 0, high = i;
}
else dp[i] = dp[low] + dp[high];
low += 2;
}
i++;
}
return dp;
}
};