美文网首页
Leetcode-233-Number of Digit One

Leetcode-233-Number of Digit One

作者: 单调不减 | 来源:发表于2019-05-30 22:40 被阅读0次

数数字的题目说难也难,说简单也简单,难就难在不重不漏,简单就简单在方法找对了,就是一个公式的事儿。

这道题的思路其实不难找,我们考虑一下什么时候会出现数字1:

1、11、21、……、91
10、11、12、……、19
100、101、……、199

我们看到,统计1在各个数位上出现的次数比较简单,不会重复也不易遗漏。我们看到11在这里出现了两次,按照数位计算的话就是十位计算一次个位计算一次,并不会产生重复。

现在的问题就是,如何计算各个数位上1的个数。

比如我们看数字142857,个位上有多少个1呢?把142857分成142857两部分,可以看到,前一部分可以取00000\sim14285,后一部分可以取1(<7),于是个位上1的个数就是14285+1=14286

下面我们看十位,同样的思路,我们把142857分成142857两部分,前一部分可以取0000\sim1428,后一部分可以取10\sim19(<57)于是十位上是1的个数为(1428+1)\times 10=14290

依次进行下去并将结果相加即为最终结果。

需要注意的特殊情况是某一位上的数字为01的情况,比如142807,我们在考查十位上数字1的个数的时候应该取1428(而非1429)\times10,因为07<10

当数字为142817,十位上数字1的个数为1428\times10+(17\% 10+1)

从而我们可以由以上规律得到一个统一的计算公式,代码如下:

class Solution {
public:
    int countDigitOne(int n) 
    {
        int res = 0;
        for (long i=1;i<=n;i*=10) 
            res+=(n/i+8)/10*i+(n/i%10==1)*(n%i+1);
        return res;
    }
};

相关文章

网友评论

      本文标题:Leetcode-233-Number of Digit One

      本文链接:https://www.haomeiwen.com/subject/veibtctx.html