题目链接:leetcode.
这道题感觉也是做过的,,可是太菜了就忘记了○| ̄|_
总结规律来说就是对于第k位每10k+1个数就会有10k个1(比如,百位即k=2,[0-999]中百位为1的就有100个数)
对于12345而言,一共有12个1000,所以百位为1的个数就是12100,但还剩下345不足1000,里面依然有百位为1的情况,即[100-199],所以百位为1共有12100 + 100个
以此类推,对于第k位,除了有(n/10k+1)*10k个1之外,还要分析t=(n%10k+1)的情况,此处能贡献min(max(t-10^k+1, 0), 10^k)个1,将k从0循环到大于n即可
/*
执行用时:0 ms, 在所有 C++ 提交中击败了100.00%的用户
内存消耗:6.2 MB, 在所有 C++ 提交中击败了5.14%的用户
*/
class Solution {
public:
int countDigitOne(int n) {
int ans = 0;
for(int k = 0;pow(10, k) <= n;++k)
{
int x = pow(10, k);
int add = (n / 10 / x) * x; //(n / (10 * x))会溢出
ans += add;
int t = n - 10 * add;
ans += min(max(t - x + 1, 0), x);
}
return ans;
}
};
本文介绍了如何利用数学规律快速计算给定整数中每个位置的1的个数,通过理解基数周期和余数分析,提供了一种高效的LeetCode解决方案。通过实例演示和代码实现,帮助读者掌握解决此类问题的方法。
1384

被折叠的 条评论
为什么被折叠?



