long res = 0;
//我觉得个位数需要特殊处理
if(n % 10 >= 1) {
res = 1;
}
//大于10的数
long a = 0;//某一位的数字
long ten = 10;//每次乘以10
long tmp = 0;//临时结果保存
//r(0~9) = 1
//r(0~99) = r(10~99) + r(0~9) = r(0~9)*9 (10~99中个位共这么多1)
// + 10(10~19中十位共10个1) + r(0~9)
// = r(0~9)*10 + 10
long cal = 1;//记录(0~9 0~99 0~999 0~9999)中1的个数
while (n / ten != 0) {
a = n / ten % 10;
if(a > 1) {
tmp = a * cal + ten;
}
else if(a == 1) {
tmp = n % ten + cal + 1; //
}
else {
tmp = 0;
}
res += tmp;
cal = cal * 10 + ten;//r(0~9 0~99 0~999)
ten = ten * 10;
}
return (int)res;
class Solution {
public int countDigitOne(int n) {
long m = 1;
int res = 0;
for(int i = 0;n>=m;i++){
res+=(n/(m*10))*m+Math.min(Math.max((n%(m*10)-m+1),0),m);
m*=10;
}
return res;
}
}
class Solution {
public int countDigitOne(int n) {
//个位数出现1的次数+百位数出现1的次数+...+n位数出现1的次数
long bit = 1;
long sum = 0;
while(bit <= n) {
long cur = (n/bit) % 10; // 第bit位上的数字
long low = n % bit;
long high = n / bit / 10;
if (cur > 1) {
sum += (high + 1) * bit;
} else if (cur == 1) {
sum += (high * bit) + (1 + low);
} else {
sum += high * bit;
}
bit = bit * 10;
}
return (int)sum;
}
}
class Solution {
public int countDigitOne(int n) {
int res = 0;
for(int i=1; i<=n; i++){
for(int j=i; j>0; j=j/10){
if(j%10 == 1){
res++;
}
}
}
return res;
}
}
2、
class Solution {
public int countDigitOne(int n) {
int res = 0;
long pow = 1;
while(pow <= n){
int high = (int)(n / pow);
int low = (int)(n % pow);
int cur = high % 10;
high = high /10;
if(cur > 1){
res += ((high + 1) * pow);
}else if(cur == 1){
res += (high*pow + low + 1);
}else {
res += high*pow;
}
pow *= 10;
}
return res;
}
}
class Solution {
public:
int countDigitOne(int n) {
long bit = 1;
long result = 0;
while (bit <= n) {
int cur = (n / bit) % 10;
int high = (n / bit) / 10;
int low = n % bit;
if (cur > 1) {
result += (high + 1) * bit;
} else if (cur == 1) {
result += high * bit + low + 1;
} else {
result += high * bit;
}
bit *= 10;
}
return int(result);
}
};
共以下 8 个回答
按照个十百千万计算,每一位和1比较,计算对应的值。首先搞清楚0-9 0-99 0-999 0-9999-中1的个数的规律。
题解学习
1、暴力法(超时了)
2、
时间复杂度O(logN), 空间复杂度O(1)