43. 从 1 到 n 整数中 1 出现的次数
解题思路
创新解法:
装逼模式开启:
我们从一个5位的数字讲起,先考虑其百位为1的情况。分3种情况讨论:
1 百位数字>=2 example: 312**56** 当其百位为>=时,有以下这些情况满足(为方便起见,计312为a,56为b):
100 ~ 199
1100 ~ 1199
…..
31100 ~ 31199
余下的都不满足!
因此,百位>=2的5位数字,其百位为1的情况有(a/10+1)*100个数字 (a/10+1)=>对应于 0 ~ 31,且每一个数字,对应范围是100个数(末尾0-99)
2 百位数字 ==1 example: 311**56** 当其百位为1时,有以下这些情况满足:
100 ~ 199
1100 ~ 1199
……
30100 ~ 30199
31100 ~ 31156
因此,百位为1的5位数字,共有(a/10)*100+(b+1)
3 百位数字 ==0 example: 310**56** 当其百位为0时,有以下这些情况满足:
100 ~ 199
1100 ~ 1199
30100 ~ 30199
其余都不满足
因此,百位数为0的5位数字,共有(a/10)*100个数字满足要求
我们可以进一步统一以下表达方式,即当百位>=2或=0时,有[(a+8)/10]100,当百位=1时,有[(a+8)/10]100+(b+1)。用代码表示就是: [(a+8)/10]*100+(a%10==1)?(b+1):0;
为什么要加8呢?因为只有大于2的时候才会产生进位等价于(a/10+1),当等于0和1时就等价于(a/10)。另外,等于1时要单独加上(b+1),这里我们用a对10取余是否等于1的方式判断该百位是否为1。
Question:有缺陷或逻辑错误吗?
有人可能会有疑惑,比如11100,这个数在考虑百位为1的时候算作了一次,在考虑千位的时候也算了一次,在考虑万位为1的时候又算了一次,一共计了3次,这不是明显重复吗?
我的回答是,不重复!
分析:题目中要我们统计出现的1的个数,那么我们可以看到11100一共是3个1,如果剔除了重复的情况只考虑一次才会是问题。换言之,在计算从1到n整数中1的出现次数时,我们把10位出现1的情况个数加上百位出现1的情况个数一直加到最高位是1的情况的个数,这里面一个数可能被统计过多次;11100百位出现1,千位和万位都为1,那么被重复统计了3次
1 |
|