題目:
解法:
第一種:直接從1到n唄,
每個數字,我們從個位,十位,到最高位分析,有多少個就加上;
然後從1遍歷到n,最後所有的加上,就是總數唄。
我們分析一下時間複雜度。每個數字的分析,肯定是lg(N)(肯定是以10爲底,n的對數)
從1到n,那麼時間複雜度就是nlogn
我沒寫,參考 https://blog.csdn.net/weixin_37672169/article/details/80950378
第二種,trick
作爲一道分析數字規律的題目,我敗了,但是查了好多博客,我感覺我參考的這種方法是最好的,爲什麼?
參考地址 :https://blog.csdn.net/littlehaes/article/details/92805867
/*
1,2,...n這n個數中
x位上每隔(x*10)個數出現x個1, n中有n/(x*10)個完整的(x*10),以百位爲例,就是n中有n/1000個完整的1000, 分別是1~~1000,1001~~2000, 2001~~3000,...(n/1000 - 1)*1000 + 1~~(n/1000)*1000
最後還可能剩下不足1000的部分, 也就是從(n/1000)*1000+1~~n, 百位的情況對應n%1000
不足(x*10)的部分,也就是n%(x*10)的部分, x位上也有可能出現1
如果n%(x*10)<x, x位上沒有1
如果n%(x*10)>2*x-1, x位上有x個1
如果n%(x*10)>=x && n%(x*10)<=2*x-1, x位上有n%(x*10) - x + 1個1
*/
public class Solution {
public int NumberOf1Between1AndN_Solution(int n) {
int count = 0;
for(int i=1; i<=n; i*=10){
count += n/(i*10) * i;
if(n%(i*10) > 2*i-1)
count += i;
else if(n%(i*10)>=i)
count += n%(i*10) - i + 1;
}
return count;
}
}