hdu5787数位dp
Posted Dirge
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了hdu5787数位dp相关的知识,希望对你有一定的参考价值。
问:L ~ R有多少个数是K-wolf Number?其中,K-wolf Number的定义是这个数在十进制下,任意相邻的K个字符没有相同的。
dp[i][j][k]表示有i个空位可填,其中不能填j这个数字中所含有的字符,k = true(表示j有前导0)时,还不能填0.
1 #include <bits/stdc++.h> 2 #define ll long long 3 #define pii pair<int, int> 4 #define mp make_pair 5 #define fi first 6 #define se second 7 using namespace std; 8 const int N = 1e5+5; 9 ll l, r; 10 int k; 11 ll dp[20][100001][2]; 12 int temp[20], tot; 13 14 ll dfs(int pos, int w, bool tag, bool flag){ 15 16 if(!pos) return 1; 17 if(flag&&~dp[pos][w][tag]) return dp[pos][w][tag]; 18 int Max = flag? 9: temp[pos]; 19 20 int ret[5], sum = 0, tmp = w; 21 while(tmp) 22 ret[sum++] = tmp%10, tmp /= 10; 23 if(tag) ret[sum++] = 0; 24 25 ll ans = 0; 26 for(int i = 0; i <= Max; i++){ 27 bool tag2 = true; 28 for(int j = 0; j < sum&&j < k-1; j++) 29 if(ret[j] == i) tag2 = false; 30 if(tag2){ 31 tmp = 0; 32 int first = min(k-2, sum-1); 33 for(int j = first; j >= 0; j--) 34 tmp = tmp*10+ret[j]; 35 bool tag3 = false; 36 if(first >= 0&&ret[first] == 0) tag3 = true; 37 ans += dfs(pos-1, tmp*10+i, tag3, flag||i != Max); 38 } 39 } 40 if(flag) dp[pos][w][tag] = ans; 41 //printf("dfs %d, %d, %d, %d %lld\n", pos, w, tag*1, flag*1, ans); 42 return ans; 43 } 44 45 ll solve(ll x){ 46 tot = 0; 47 while(x){ 48 temp[++tot] = x%10; 49 x /= 10; 50 } 51 return dfs(tot, 0, 0, 0); 52 } 53 int main(){ 54 while(cin >> l >> r >> k){ 55 memset(dp, -1, sizeof(dp)); 56 ll ans = solve(r)-solve(l-1); 57 cout << ans << endl; 58 } 59 return 0; 60 }
以上是关于hdu5787数位dp的主要内容,如果未能解决你的问题,请参考以下文章