数位dp

FZU2109 数位dp 含前导零

吃可爱长大的小学妹 提交于 2019-11-27 13:39:55
这题没考虑到前导0,就是不知道哪wa了,又补题一直wa,scanf和printf改成cin cout就对了 真不知道错在哪了。。。刚刚又试了一下,G++scanf过不了 但是visual C++可以。真服了,浪费我又一个多小时。 这道题是简单的数位dp!!!注意前导0!前导0!前导0!掉坑的地方说三遍,顺便庆祝下因为前导0,成功爆0。 思路:就是数位dp模板题,不过置前导0的时候要注意技巧,就是num要放9。为什么放9呢?因为放9不会限制后面取数。暂且这么记吧,我真没整明白为啥放9呜呜呜。 下面是AC代码!一定要掌握前导0的处理! # include <cstdio> # include <iostream> # include <cstring> # include <cmath> # include <algorithm> # define ll long long # define maxn 20 using namespace std ; //这题注意前导0!!! int dig [ maxn ] ; ll dp [ maxn ] [ maxn ] [ 2 ] ; ll dfs ( int pos , int num , int odd , int pre0 , int limit ) { if ( ! pos ) return 1 ; if ( ! limit && dp

BZOJ 3679 数字之积 数位DP

旧巷老猫 提交于 2019-11-27 13:37:29
思路:数位DP 提交: \(2\) 次 错因:进行下一层 \(dfs\) 时的状态转移出错 题解: 还是记忆化搜索就行,但是要用 \(map\) 记忆化。 见代码 #include<cstdio> #include<iostream> #include<map> #define R register int #define ll long long using namespace std; namespace Luitaryi { template<class I> inline I g(I& x) { x=0; register I f=1; register char ch; while(!isdigit(ch=getchar())) f=ch=='-'?-1:f; do x=x*10+(ch^48); while(isdigit(ch=getchar())); return x*=f; } ll n,l,r,num[19],len,stk[19],top; map<ll,ll> f[20]; inline void print() { for(R i=1;i<=top;++i) cout<<stk[i]; } inline ll dfs(int l,bool ul,bool ck,ll ml) { if(l==0) {return ml<=n&&ml>0?1:0;} if(

1043 幸运号码 (简单数位dp)

眉间皱痕 提交于 2019-11-27 10:39:51
1043 幸运号码 1个长度为2N的数,如果左边N个数的和 = 右边N个数的和,那么就是一 个幸运号码。 例如:99、1230、123312是幸运号码。 给出一个N,求长度为2N的幸运号码的数量。由于数量很大,输出数量 Mod 10^9 + 7的结果即可。 输入 输入N(1<= N <= 1000) 输出 输出幸运号码的数量 Mod 10^9 + 7 输入样例 1 输出样例 9 思路: 这题一开始考虑前后两个N位数重复会造成答案冗余,其实 是我自己考虑错了,计算出N位数构造和为sum有多少种方案, 然后 不带前导零的方案数 * 带前导零的方案数即可。 dp数组第二维范围开小了,WA,自己一直考虑,这题答案 要不要处理负数模的情况,不处理也能过,但应该处理吧?还是 不会出现负数情况? 代码实现: #include <iostream> #include <string.h> #include <math.h> #include <ctime> #include <bits/stl_algo.h> #include <stdio.h> #include <algorithm> #define LL long long #define INF 0x3f3f3f3f #define ull unsigned long long using namespace std; const int

bzoj3209: 花神的数论题(数位DP)

*爱你&永不变心* 提交于 2019-11-27 10:13:32
题目: 3209: 花神的数论题 解析: 二进制的数位DP 因为 \([1,n]\) 中每一个数对应的二进制数是唯一的,我们枚举 \(1\) 的个数 \(k\) ,计算有多少个数的二进制中有 \(k\) 个 \(1\) 设 \(n\) 的二进制一共有 \(num\) 位,有 \(sum[i]\) 个数的二进制中有 \(k\) 个 \(1\) , 答案就是 \(\prod_{i=1}^{num}i^{sum[i]}\) 用数位DP搞一下就好了 设 \(f[i][j]\) 表示到第 \(i\) 位有 \(j\) 个 \(1\) 时有多少个数 枚举 \(k\) ,记搜一下。 由于可能会有很多数的二进制中有 \(k\) 个 \(1\) ,所以用快速幂维护一下 相似思路的题还有 1799: [Ahoi2009]self 同类分布 代码: #include <bits/stdc++.h> #define int long long using namespace std; const int N = 60; const int mod = 10000007; int n, m, num; int digit[N], f[N][N]; int qpow(int a, int b) { int ans = 1; while (b) { if (b & 1) ans = (ans * a) %

不要62(数位DP)

南笙酒味 提交于 2019-11-27 09:30:46
 杭州人称那些傻乎乎粘嗒嗒的人为62(音:laoer)。  杭州交通管理局经常会扩充一些的士车牌照,新近出来一个好消息,以后上牌照,不再含有不吉利的数字了,这样一来,就可以消除个别的士司机和乘客的心理障碍,更安全地服务大众。 不吉利的数字为所有含有4或62的号码。例如:  62315 73418 88914 都属于不吉利号码。但是,61152虽然含有6和2,但不是62连号,所以不属于不吉利数字之列。 你的任务是,对于每次给出的一个牌照区间号,推断出交管局今次又要实际上给多少辆新的士车上牌照了。 Input  输入的都是整数对n、m(0<n≤m<1000000),如果遇到都是0的整数对,则输入结束。 Output  对于每个整数对,输出一个不含有不吉利数字的统计个数,该数值占一行位置。 Sample Input 1 100 0 0 Sample Output 80 题意: 求数字n到m中不含有“62”和“4”的数字个数。 思路: 数位DP,从最高位一位一位看,不重不漏 代码: 1 #include <stdio.h> 2 #include <string.h> 3 4 int a[100], dp[100][2]; 5 6 int dfs(int cur, int limit, int rem) 7 //cur表示当前操作的是哪一位 8 //limit=1时小心超过n和m 9 /

数据结构-数位dp

瘦欲@ 提交于 2019-11-27 05:48:46
不了解dp的可以先看一下 dp 数位dp含义: 数位:一个数有个位,十位,百位,千位等等,数的每一位都是数位。 数位dp归为计数 dp, 是在数位上进行操作的dp。 数位dp的实质是一种快速枚举的方式,它满足dp的性质,然后进行记忆化搜索。 用途: 有两个数,两个数范围很大(例如1e9,甚至更大),求这两个数符合限定条件的个数。纯暴力不行,就要用数位dp。 例子:求从0到n,(n为2^32-1),(条件)求包含49的数有多少; 思路or具体实现: n为2^32-1,数位其实只有20位,枚举数位,就不会超时。 dp[shuwei][diaojian]。dp的第一维通常是数位,后面的几维根据题目条件来设定。上面给的例子只用了一维。 控制上界枚举,从最高位往下枚举。用记忆化搜索来做,抛开循环后转移状态能更加随意,大部分数位和动态规化的题都可随意切换。搜索与循环异曲同工之妙,但前者更易转移状态,在限制较多的情况下被大部分人喜爱。 例题: Bomb 思路 :数位dp=dfs+记忆化搜索。 需要注意上限即题目所给范围的预处理,本题用digtis[20] 数组,存储上限的数位,最好用一个函数来处理,比如solve(sum),处理时,对上限的数位总数拿一个变量进行存储,比如k或len。 在dfs中用 limit (有些题解是top)判定上限,dfs(len,条件,limit); dfs执行数位dp

[BZOJ5064] [HDU3652] B-number 数位DP

大城市里の小女人 提交于 2019-11-27 04:33:52
题目描述 B数的定义:能被13整除且本身包含字符串"13"的数。 例如:130和2613是B数,但是143和2639不是B数。 你的任务是计算1到n之间有多少个数是B数。 输入 输入数据只有一个数,为n。( \(1<=N<=10^{15}\) ) 输出 输出数据包含一行,为1到n之间B数的个数。 样例输入 13 样例输出 1 题解 数位DP 记录对13的模数来判断是否可以被13整除。 同时记录是否出现过‘13’, 还要考虑首位前导0的情况。 设 \(f[i][j][k][0/1]\) 为 \(i\) 位数,对 \(13\) 取模结果为 \(j\) ,首位为 \(k\) ,是否包含 \(13\) 的数的个数。 预处理 \(f\) 数组后进行数位DP。 先填充位数不满的,再由高位向低位将此位不满的加入答案。 转换询问区间为 \([1,n)\) 则更易简单处理。 code #include <iostream> #include <cstdio> using namespace std; typedef long long LL; LL n, b[17], f[17][13][10][2]; void init() { b[0] = f[0][0][0][0] = 1; for(int i = 1;i <= 16;i ++) { b[i] = b[i-1] * 10; for(int j

[HDU3555] Bomb 数位DP

寵の児 提交于 2019-11-27 04:32:39
Problem Description The counter-terrorists found a time bomb in the dust. But this time the terrorists improve on the time bomb. The number sequence of the time bomb counts from 1 to N. If the current number sequence includes the sub-sequence "49", the power of the blast would add one point. Now the counter-terrorist knows the number N. They want to know the final points of the power. Can you help them? Input The first line of input consists of an integer T (1 <= T <= 10000), indicating the number of test cases. For each test case, there will be an integer N (1 <= N <= 2^63-1) as the

hdu2089 不要62(数位dp)

孤者浪人 提交于 2019-11-27 03:29:45
不要62 本题大意:不吉利数字为62和4,求给定区间内的不吉利数的个数。 最为基础的数位dp入门题,不过本弱鸡水平太低,对着函数死看看不懂,只能当作模版用了,solve(x)表示x以内的不吉利数字的个数,用右区间减去左区间即可。 #include <iostream> #include<cstdio> #include <algorithm> #include <string> #include <cstring> #include <map> #include <set> #include <stack> #include <cmath> #include <queue> #include <vector> #define init(){ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);} using namespace std; typedef long long ll; int a[20]; ll dp[20][2]; ll dfs(int pos, int pre, int state, bool limit) { if(pos==-1) return 1; if(!limit && dp[pos][state]!=-1) return dp[pos][state]; int up=limit?a[pos]:9; ll

dp专题训练

本小妞迷上赌 提交于 2019-11-26 21:41:33
****************************************************************************************** 动态规划 专题训练 ******************************************************************************************** 一、简单基础dp 这类dp主要是一些状态比较容易表示,转移方程比较好想,问题比较基本常见的。 1、递推: 递推一般形式比较单一,从前往后,分类枚举就行。 入门: hdu 2084 数塔 简单从上往下递推 hdu 2018 母牛的故事 简单递推计数 hdu 2044 一只小蜜蜂... 简单递推计数(Fibonacci) hdu 2041 超级楼梯 Fibonacci 推荐: CF 429B B.Working out 四个角递推 zoj 3747 Attack on Titans 带限制条件的计数递推dp hdu 2050 折线分割平面 找递推公式 uva 10328 Coin Toss 同上题 hdu 4747 Mex hdu 4489 The King's Ups and Downs hdu 4054 Number String 2、背包 经典的背包九讲: http://love-oriented