[Sdoi2014]数数[数位dp+AC自动机]
3530: [Sdoi2014]数数
Time Limit: 10 Sec Memory Limit: 512 MB
Submit: 834 Solved: 434
[Submit][Status][Discuss]
Description
我们称一个正整数N是幸运数,当且仅当它的十进制表示中不包含数字串集合S中任意一个元素作为其子串。例如当S=(22,333,0233)时,233是幸运数,2333、20233、3223不是幸运数。
给定N和S,计算不大于N的幸运数个数。
Input
输入的第一行包含整数N。
接下来一行一个整数M,表示S中元素的数量。
接下来M行,每行一个数字串,表示S中的一个元素。
Output
输出一行一个整数,表示答案模109+7的值。
Sample Input
3
2
3
14
Sample Output
HINT
下表中l表示N的长度,L表示S中所有串长度之和。
1 < =l < =1200 , 1 < =M < =100 ,1 < =L < =1500
Source
#include<cstdio>
#include<cstring>
using namespace std;
typedef long long ll;
const int N=;
const int mod=1e9+;
int n,m,len,cnt=,b[N],c[N],w[N],fail[N],tr[N][],q[N];
char a[N];
int f[N][N][];ll ans;
inline void insert(int *s){
int now=;
for(int i=;i<=len;i++){
if(!tr[now][s[i]]) tr[now][s[i]]=++cnt;
now=tr[now][s[i]];
}
w[now]++;
}
inline void AC_mach(){
for(int i=;i<=;i++) tr[][i]=;
int p,h=,t=;q[t]=;fail[]=;
while(h!=t){
int now=q[++h];
for(int i=;i<=;i++){
if(tr[now][i]){
for(p=fail[now];!tr[p][i];p=fail[p]);
fail[tr[now][i]]=tr[p][i];
q[++t]=tr[now][i];
}
}
}
}
inline void dp(int T){
for(int i=,p;i<=cnt;i++){
for(int l=;l<=;l++){
if(w[i]||!f[T-][i][l]) continue;
for(int j=;j<=;j++){
for(p=i;!tr[p][j];p=fail[p]);
f[T][tr[p][j]][l+j>b[T]]=(f[T][tr[p][j]][l+j>b[T]]+f[T-][i][l])%mod;
if(!j) f[T][tr[p][j]][]=(f[T][tr[p][j]][]+f[T-][i][l])%mod;//前导0
}
}
}
}
int main(){
freopen("count.in","r",stdin);
freopen("count.out","w",stdout);
scanf("%s",a+);n=strlen(a+);
for(int i=;i<=n;i++) b[n-i+]=a[i]-'';
scanf("%d",&m);
for(int i=;i<=m;i++){
scanf("%s",a+);len=strlen(a+);
for(int j=;j<=len;j++) c[len-j+]=a[j]-'';
insert(c);
}
AC_mach();
f[][][]=;
for(int i=;i<=n;i++) dp(i);
for(int i=;i<n;i++){
for(int j=;j<=cnt;j++){
if(!w[j]){
ans=(ans+(ll)f[i][j][]+f[i][j][]-f[i][j][])%mod;
}
}
}
for(int i=;i<=cnt;i++){
if(!w[i]){
ans=(ans+(ll)f[n][i][]-f[n][i][])%mod;
}
}
printf("%lld",ans);
return ;
}
[Sdoi2014]数数[数位dp+AC自动机]的更多相关文章
- 咕咕(数位dp+AC自动机)
咕咕(数位dp+AC自动机) 若一个字符串的字符集合是0~m-1,那么称它为m进制字符串.给出n个m进制字符串\(s_i\),每个字符串的权值为\(v_i\).对于另一个m进制字符串\(S\),设\( ...
- 2019.02.15 codechef Favourite Numbers(二分+数位dp+ac自动机)
传送门 题意: 给444个整数L,R,K,nL,R,K,nL,R,K,n,和nnn个数字串,L,R,K,数字串大小≤1e18,n≤65L,R,K,数字串大小\le1e18,n\le65L,R,K,数字 ...
- CF 434C Tachibana Kanade's Tofu[数位dp+AC自动机]
Solution //本代码压掉后两维 #include<cstdio> #define max(a,b) (a<b?b:a) using namespace std; inline ...
- BZOJ_1662_[Usaco2006 Nov]Round Numbers 圆环数_数位DP
BZOJ_1662_[Usaco2006 Nov]Round Numbers 圆环数_数位DP Description 正如你所知,奶牛们没有手指以至于不能玩“石头剪刀布”来任意地决定例如谁先挤奶的顺 ...
- BZOJ_1026_[SCOI2009]windy数_数位DP
BZOJ_1026_[SCOI2009]windy数_数位DP 题意:windy定义了一种windy数.不含前导零且相邻两个数字之差至少为2的正整数被称为windy数. windy想知道, 在A和B之 ...
- 洛谷$P4045\ [JSOI2009]$密码 $dp$+$AC$自动机
正解:$dp$+$AC$自动机+搜索 解题报告: 传送门$QwQ$ 首先显然先建个$AC$自动机,然后考虑设$f_{i,j,k}$表示长度为$i$,现在在$AC$自动机的第$j$个位置,已经表示出来的 ...
- [bzoj 1026]windy数(数位DP)
题目:http://www.lydsy.com/JudgeOnline/problem.php?id=1026 分析: 简单的数位DP啦 f[i][j]表示数字有i位,最高位的数值为j的windy数总 ...
- bzoj 1026 [SCOI2009]windy数(数位DP)
1026: [SCOI2009]windy数 Time Limit: 1 Sec Memory Limit: 162 MBSubmit: 4550 Solved: 2039[Submit][Sta ...
- [BZOJ 1026] [SCOI 2009] Windy数 【数位DP】
题目链接:BZOJ - 1026 题目分析 这道题是一道数位DP的基础题,对于完全不会数位DP的我来说也是难题.. 对于询问 [a,b] 的区间的答案,我们对询问进行差分,求 [0,b] - [0,a ...
随机推荐
- Python 最火 IDE 最受欢迎(转载)
来自:开源中国社区 链接:https://www.oschina.net/news/86973/packt-skill-up-2017 电子书网站 Packt 刚刚发布了第三届 “Skill UP” ...
- kata-container环境搭建
一.安装qemu 注意,目前kata-container所要求的qemu最低版本是v2.7.0.在笔者的环境下(Ubuntu16.04 VM),apt-get官方源的最高版本是v2.5.0.所以不要用 ...
- Yum编译安装Error Downloading Packages报错
1:执行yum clean all 清除缓存目录下的软件包及旧的headers: 2:接着执行 yum list重新列出所有已经安装和可以安装的软件包: 3:重新执行上述命令,发现yum编译成功: 注 ...
- MySql中文乱码问题(3)
MySql的client是在dos界面上,然而dos界面默认的字符集编码方式是:GBK (1).MySql字符转换原理图 watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi ...
- NodeJS中的循环陷阱
Node.js的异步机制由事件和回调函数实现,一開始接触可能会感觉违反常规,但习惯以后就会发现还是非常easy的. 然而这之中事实上暗藏不少陷阱.一个非常easy遇到的问题就是回到循环的回调函数. e ...
- SQL语句练习手册--第四篇
一.变量那点事儿 1.1 局部变量 (1)声明局部变量 DECLARE @变量名 数据类型 ) DECLARE @id int (2)为变量赋值 SET @变量名 =值 --set用于普通的赋值 SE ...
- Acceptor-Connector模式一(Acceptor的工作)V2.0
前言:ACE Acceptor-Connector模式 首先这样的模式肯定是面向连接的TCP/IP协议. 无论是什么场景.差点儿面向连接的通信程序总是由一端主动发起连接,一端监听等待对方的连接. 这就 ...
- .net 取当前代码的行号及类名称
取方法入口的行号及类名 //System.Diagnostics.StackTrace st = new System.Diagnostics.StackTrace(1, true); //int a ...
- linux系统下面ftp的一些命令
service vsftpd restart重启vsftpd服务service vsftpd stop停止vsftpd服务service vsftpd start启动vsftpd服务 chkconfi ...
- HDU 4417 划分树+二分
题意:有n个数.m个询问(l,r,k),问在区间[l,r] 有多少个数小于等于k. 划分树--查找区间第k大的数.... 利用划分树的性质.二分查找在区间[l,r]小于等于k的个数. 假设在区间第 i ...