UVA 1640 The Counting Problem(统计题,找规律 + dfs)

    xiaoxiao2021-03-25  104

    大体题意:

    告诉你两个数a和b 问你a到b 区间内的数中,0,1,2,3,4,5,6,7,8,9每个数字出现了几次?

    思路:

    我们先写一个暴力的程序会找到一个规律:

    除了0以外的9个数字:

    9以内有1个 = num[1]

    99以内有20个 = num[2]

    999以内的有300个 = num[3]

    9999以内的有4000个 = num[4]

    依次类推:

    我们可以根据这个规律来写:

    比如说997内 找4的个数

    百分位为0 1 2 3 5 6 7 8 的都有num[2]个 。

    在来算百分位为4的,去掉9以后  为97,那么就有98个4.

    在dfs  97中4 的个数。

    在算百分位为9的,直接加dfs 97中4的个数即可。

    这样1~9都算完了,还有0的没算。

    我们可以算一个数 中所有数字出现了几次,用总和减去1~9的即可:

    #include <cstdio> #include <cstring> #include <algorithm> #include <vector> #define Siz(x) (int)x.size() using namespace std; typedef long long LL; int num[] = {1,1,20,300,4000,50000,600000,7000000,80000000,900000000}; int getlen(int x){ if (x == 0) return 1; int ans=0; while(x) { ++ans; x/=10; } return ans; } int get_first(int x){ if (x == 0) return 0; while(x/10){ x/=10; } return x; } LL getall(int x){ LL ans = 0; int cur = 1; int L = 0,R = 9; while( !(x >= L && x <= R) ){ ans += cur*(R-L+1); L = R+1; cur++; R = R*10+9; } ans += (x-L+1)*cur; return ans; } int dfs(int x,int v,int len){ if (len == 1){ if (x >= v) return 1; return 0; } int ans = 0; int f = get_first(x); int v2 = 1; for (int i = 0; i < len-1; ++i) v2*=10; int x2 = x - f*v2; if (f > v){ for (int i = f-1; i > v; --i){ ans += num[len-1]; } for (int i = v-1; i >= 0; --i)ans += num[len-1]; ans += v2 + num[len-1]; ans += dfs(x2,v,getlen(x2)); } else if (f == v){ for (int i = v-1; i >= 0; --i)ans += num[len-1]; ans += x2+1 + dfs(x2,v,getlen(x2)); } else { for (int i = f-1; i >= 0; --i)ans += num[len-1]; ans += dfs(x2,v,getlen(x2)); } return ans; } vector<int>ans; int main(){ // freopen("out.txt","w",stdout); int a,b; while(~scanf("%d %d",&a, &b) && (a||b)){ if (a > b) swap(a,b); ans.clear(); LL sum = 0LL; for (int i = 1; i <= 9; ++i){ ans.push_back(dfs(b,i,getlen(b)) - dfs(a-1,i,getlen(a-1))); sum += ans.back(); } ans.push_back(getall(b) - getall(a-1)); printf("%lld",ans.back()-sum); for (int i = 0; i < 9; ++i)printf(" %d",ans[i]); putchar('\n'); } return 0; } /** 1496 1403 **/

    转载请注明原文地址: https://ju.6miu.com/read-24571.html

    最新回复(0)