[集训笔记6th]dp进阶之数位dp
2019-08-12 18:21
134 查看
版权声明:本文为博主原创文章,遵循 CC 4.0 by-sa 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/qq_43279710/article/details/99075220
学习自:https://www.geek-share.com/detail/2681206279.html
通过一个代码片来看数位dp的特点
for(int i = l; l <= r; i++){ if(check(i) == true) cnt++; }
check就是题目的某些约束条件。
一般是求区间内满足条件的数目。
hdu2089 不要62 (和4
模板题:求[l, r]内满足不含4且不含"62"的数的数量。
dp中的i表示从左往右当前位数,j表示上限数字前一位的对这一位的限制。比如这个题,因为不能含62,所以前一位含不含6就将dp分成了两组。
solve返回的是从1到x,有多少满足条件的数字。
#include <iostream> #include <cstdio> #include <cstring> #include <string> using namespace std; typedef long long ll; int a[20]; int dp[20][2]; int dfs(int pos, int pre, int sta, bool limit){ if(pos == -1) return 1; if(!limit && dp[pos][sta] != -1) return dp[pos][sta]; int up = limit ? a[pos] : 9; int tmp = 0; for(int i = 0; i <= up; i++){ if((pre == 6 && i == 2) || i == 4) continue; tmp += dfs(pos - 1, i, i==6, limit && i == a[pos]); } if(!limit) dp[pos][sta] = tmp; return tmp; } int solve(int x){ int pos = 0; while(x){ a[pos++] = x % 10; x /= 10; } return dfs(pos-1, -1, 0, true); } int main(){ int l, r; while(~scanf("%d%d", &l, &r) , l&&r){ memset(dp, -1, sizeof(dp)); printf("%d\n", solve(r) - solve(l - 1)); } return 0; }
相关文章推荐
- [集训笔记7th]dp进阶之树形dp hdu1054
- [暑假集训--数位dp]hdu3709 Balanced Number
- hdu 3886 Final Kichiku “Lanlanshu(数位DP进阶)
- [暑假集训--数位dp]hdu5898 odd-even number
- poj Round Numbers 3252(数位dp进阶)
- [暑假集训--数位dp]LightOj1032 Fast Bit Calculations
- [暑假集训--数位dp]LightOJ1140 How Many Zeroes?
- [暑假集训--数位dp]LightOj1205 Palindromic Numbers
- 陕西省集训(数位dp)
- [暑假集训--数位dp]hdu2089 不要62
- [暑假集训--数位dp]UESTC250 windy数
- 【学习笔记&训练记录】数位DP
- XDU2019寒假集训:week3 DP进阶
- [暑假集训--数位dp]hdu5787 K-wolf Number
- 数位DP进阶-HDU2089不要62
- [暑假集训--数位dp]hdu3652 B-number
- 数位dp进阶题目——较复杂的状态刻画
- UOJ275 [清华集训2016] 组合数问题 【Lucas定理】【数位DP】
- 【算法笔记】数位dp小结
- 数位dp笔记