数位DP入门题 hdu 2089 hdu 3555
hdu 2089 不要62
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2089
题意:对于每次给出的一个区间,找出区间内多少个数字没有出现62和4。
思路:
数位DP入门题,对于dfs设置3个参数。
一个表示现在进行到第几位,
一个表示前一个标记状态,这里表示上一位是不是6。
一个表示是否现在是这位可以取到的最大的数字。
如果上一位是6,那么这位不可以取2。且当前位都不可以取4。
1 #include <bits/stdc++.h> 2 using namespace std; 3 int dp[10][2], num[10]; 4 int dfs(int cur, int state, int limit) 5 { 6 if(cur < 0) return 1; 7 if(!limit && dp[cur][state] != -1) return dp[cur][state]; 8 9 int ret = 0; 10 int up = limit?num[cur]:9; 11 for(int i = 0; i <= up; i++) 12 { 13 if(state == 1 && i == 2 || i == 4) continue; 14 else ret += dfs(cur-1, i == 6, limit && i == up); 15 } 16 if(!limit) dp[cur][state] = ret; 17 return ret; 18 19 } 20 int slove(int x) 21 { 22 memset(dp, -1, sizeof(dp)); 23 int cnt = 0; 24 while(x) 25 { 26 num[cnt++] = x % 10; 27 x /= 10; 28 } 29 return dfs(cnt-1, 0, 1); 30 } 31 int main() 32 { 33 // freopen("in.txt", "r", stdin); 34 // freopen("out.txt", "w", stdout); 35 int n, m; 36 while(~scanf("%d%d", &n, &m) && n+m) 37 { 38 printf("%d\n", slove(m) - slove(n-1)); 39 } 40 return 0; 41 }
hdu 3555 bomb
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3555
题意:找出1-N中出现49的数字个数。
思路:和上题差不多,如果前几位出现4,则这位不能出现9。
1 #include <bits/stdc++.h> 2 using namespace std; 3 int T; 4 int num[30]; 5 long long dp[30][2]; 6 long long dfs(int cur, int state, int limit) 7 { 8 if(cur < 0) return 1; 9 if(!limit && dp[cur][state] != -1) return dp[cur][state]; 10 11 long long ret = 0; 12 int up = limit?num[cur]:9; 13 for(int i = 0; i <= up; i++) 14 { 15 if(state && i == 9) continue; 16 ret += dfs(cur-1, i == 4, limit && i == up); 17 } 18 if(!limit) dp[cur][state] = ret; 19 return ret; 20 } 21 long long slove(long long x) 22 { 23 memset(dp, -1, sizeof(dp)); 24 int cnt = 0; 25 while(x) 26 { 27 num[cnt++] = x%10; 28 x /= 10; 29 } 30 return dfs(cnt-1, 0, 1); 31 } 32 long long N; 33 int main() 34 { 35 // freopen("in.txt", "r", stdin); 36 // freopen("out.txt", "w", stdout); 37 scanf("%d", &T); 38 while(T--) 39 { 40 scanf("%lld", &N); 41 printf("%lld\n", N+1-slove(N)); 42 } 43 44 return 0; 45 }