[LintCode] Digit Counts

Problem

Count the number of k's between 0 and n. k can be 0 - 9.

Example

if n=12, k=1 in [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12], we have FIVE 1's (1, 10, 11, 12)

Note

先分析这段计数2的代码:

最后的else很好理解,(高位*base)+(大于k的当前位*base)即可;
cur < k时的分支也很好理解,当前位没有k,只算高位的即可;
最上面的if比较难理解,其实low+1和base比起来,就是当前位k在这一位上有low+1个k,如125求2的十位,low=5,有5+1=6(120,121,122,123,124,125)个2。

if (cur == k) {result += high * base + low + 1;} 
else if (cur < k) {result += high * base;} 
else {result += (high + 1) * base;}

举个例子:

//222,2: (22 + 1)  +  (20 + 2 + 1)  +  (22 + 1)
           个位2           十位2          百位2

个位有22+1个2,包括第一个2

//12 22 32 42 52 62 72 82 92 102
//112 122 132 142 152 162 172 182 192 202 212 222 (02)

十位有20个2加上(2+1)个在220之后的2,共计20+3

//20 21 22 23 24 25 26 27 28 29
//120 121 122 123 124 125 126 127 128 129 (221 222, 220)

百位有22+1个2

//201 202 203 204 205 206 207 208 209 210
//211 212 213 214 215 216 217 218 219 220 221 222 (200)

Solution

public int digitCounts(int k, int n) {
        // write your code here
        int result = 0; 
        int base = 1;  //当前位数 初始化:个位
        while (n/base > 0 && k != 0) {
            int cur = (n / base) % 10; //当前位
            int low = n - (n/base) * base; //更低位
            int high = n/(base * 10); //更高位
            //当前位和k的关系不论如何,都有(更高位*base)的累加
            if (cur == k) {
                result += high * base + low + 1; //+1是什么意思呢
            } 
            else if (cur < k) {
                result += high * base;
            } 
            else {
                result += (high + 1) * base;
            }
            base *= 10;
        
        }
        if (k == 0) {
            result = 1;
            while (n/base > 0) {
                int cur = (n / base) % 10;
                int high = n/(base * 10);
                int low = n - (n/base) * base;
                result += high * base;
                base *= 10;
            }
        }
        return result;
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值