见 AC自动机(补坑了)

[SDOI2014] 数数

简要题意: 

我们称一个正整数N是幸运数,当且仅当它的十进制表示中不包含数字串集合S中任意一个元素作为子串。例如当S={22,333,0233}时,233是幸运数,2333、20233、3223都不是幸运数。给定N和S,计算不大于N的幸运数个数。

分析: 

这道题是 数位dp + AC自动机,之前kzsn并没有学数位dp,所以学AC自动机的时候并不怎么会。

但如今,kzsn转型换代,终于懂了一点点数位dp的皮毛。

首先我们定个dp的状态 dp[pos][x],表示数位dp到第pos位,当前数字的状态位于AC自动机的x处。

这个状态怎么转移呢?

我们枚举下一位取的数字 $i$,如果$go[x][i]$处没有标记,即表示当前没有子串在当前数中,可以转移过去。

dp[pos][x] += dp[pos-1][go[x][i]];

那么这道题就做完了!!!

好耶!记忆化的数位dp是真的好写。

#include<bits/stdc++.h>
using namespace std;
#define re register int
#define int long long const int mo = 1e9+7;
int go[2000][20], mark[2000], fail[2000], total;
void insert(string s)
{
int p=0;
for(re i=0, sz=s.length();i<sz;++i)
{
int x=s[i]-'0';
if(!go[p][x])go[p][x]=++total;
p=go[p][x];
}
mark[p]=1;
}
void build()
{
queue<int>Q;
for(re i=0;i<=9;++i)if(go[0][i])Q.push(go[0][i]);
while(!Q.empty())
{
int x=Q.front();
Q.pop(); mark[x]|=mark[fail[x]];
for(re i=0;i<=9;++i)
{
int t=go[x][i];
if(!t) go[x][i] = go[fail[x]][i];
else
{
Q.push(t);
fail[t] = go[fail[x]][i];
}
}
}
} int dp[2000][2000], num[2000];
int DFS(int pos, int x, int limit, int lead)
{
if(mark[x])return 0;
if(!pos)return 1;
int &ans = dp[pos][x];
if(!limit && ~ans) return ans; int ret = 0, up = limit ? num[pos] : 9;
for(re i=0;i<=up;++i)
{
if(i == 0 && lead) ret += DFS(pos-1, x, limit && i == up, 1);
else
{
int v = go[x][i];
if(!mark[v])
ret += DFS(pos-1, v, limit && i == up, 0);
while(ret>=mo)ret-=mo;
}
}
return limit ? ret : ans = ret;
}
int solve(string a)
{
memset(dp, -1, sizeof dp);
int len = a.length();
for(re i=0;i<len;++i) num[len-i] = a[i]-48;
return DFS(len, 0, 1, 1);
}
signed main()
{
string n;int m;
cin>>n>>m;
while(m--)
{
string s;
cin>>s;
insert(s);
}
build();
printf("%lld", ((solve(n)-1)%mo+mo)%mo);
return 0;
}

【SDOI2014】数数(补)的更多相关文章

  1. 【BZOJ】【3530】【SDOI2014】数数

    AC自动机/数位DP orz zyf 好题啊= =同时加深了我对AC自动机(这个应该可以叫Trie图了吧……出边补全!)和数位DP的理解……不过不能自己写出来还真是弱…… /************* ...

  2. BZOJ3530: [Sdoi2014]数数

    3530: [Sdoi2014]数数 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 322  Solved: 188[Submit][Status] ...

  3. 【HDU3530】 [Sdoi2014]数数 (AC自动机+数位DP)

    3530: [Sdoi2014]数数 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 682  Solved: 364 Description 我们称一 ...

  4. BZOJ 3530: [Sdoi2014]数数 [AC自动机 数位DP]

    3530: [Sdoi2014]数数 题意:\(\le N\)的不含模式串的数字有多少个,\(n=|N| \le 1200\) 考虑数位DP 对于长度\(\le n\)的,普通套路DP\(g[i][j ...

  5. 「SDOI2014」数数 解题报告

    「SDOI2014」数数 题目描述 我们称一个正整数 \(N\) 是幸运数,当且仅当它的十进制表示中不包含数字串集合 \(S\) 中任意一个元素作为其子串. 例如当 \(S=(\)22, 333, 0 ...

  6. 3530: [Sdoi2014]数数

    3530: [Sdoi2014]数数 链接 分析: 对给定的串建立AC自动机,然后数位dp.数位dp的过程中,记录当前在AC自动机的哪个点上,保证不能走到出现了给定串的点. 代码: #include& ...

  7. [SDOI2014]数数 --- AC自动机 + 数位DP

    [SDOI2014]数数 题目描述: 我们称一个正整数N是幸运数,当且仅当它的十进制表示中不包含数字串集合S中任意一个元素作为其子串. 例如当S=(22,333,0233)时,233是幸运数,2333 ...

  8. bzoj [Sdoi2014]数数 AC自动机上dp

    [Sdoi2014]数数 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 1264  Solved: 636[Submit][Status][Discu ...

  9. [Sdoi2014]数数[数位dp+AC自动机]

    3530: [Sdoi2014]数数 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 834  Solved: 434[Submit][Status][ ...

随机推荐

  1. AQS学习(二) AQS互斥模式与ReenterLock可重入锁原理解析

    1. MyAQS介绍    在这个系列博客中,我们会参考着jdk的AbstractQueuedLongSynchronizer,从零开始自己动手实现一个AQS(MyAQS).通过模仿,自己造轮子来学习 ...

  2. python库--pandas--MultiIndex

    *表示后面会重复用到此参数 创建层次化索引 pd.MultiIndex 构造器 MI levels 每个级别不重复的标签 labels 每个级别的整数指定每个位置 *sortorder=None   ...

  3. Vue3.x全家桶+vite+TS-搭建Vue3.x项目

    目录 一.搭建基础项目 1.vite创建项目 3.运行项目 2.环境变量设置介绍 vite配置多环境打包 二.配置Router 1.安装路由 2.配置路由 3.引入 三.配置Vuex 1.安装vuex ...

  4. UVA 506 System Dependencies(模拟 烂题)

    https://vjudge.net/problem/UVA-506 题目是给出了五种指令,DEPEND.INSTALL.REMOVE.LIST.END,操作的格式及功能如下: DEPEND item ...

  5. NOIP初赛:完善程序做题技巧

    最近写的文章好像还很多的.那么今天我们来讨论NOIP初赛的题型--完善程序.完善程序相对是比较难的题目了.全卷100分,完善程序占了大概26分,占比非常大.如果和英语考试试卷做比较,相当于首字母填空( ...

  6. Mysql实现无插入有更新(不知主键的情况下)

    网上很多资料说有两种方式 (必须现有唯一键) 1.INSERT 中ON DUPLICATE KEY UPDATE的使用 2.REPLACE的使用 通过可以得出结果: 如果a和b字段 能决定唯一 例子: ...

  7. Linux系列(32) - rpm命令管理之RPM查询(4)

    RPM包默认安装位置 RPM包默认安装路径 /etc/ 配置文件安装目录 /usr/bin/ 可执行的命令安装目录 /usr/lib/ 程序所使用的函数库保存位置 /usr/share/doc/ 基本 ...

  8. ubuntu系统执行生成密匙命令后,home目录下面没有生成.ssh目录

    ubuntu系统配置git ssh时,执行:ssh-keygen -trsa -C "youremail@example.com",home目录下面没有生成.ssh目录. .ssh ...

  9. .NET 排序 Array.Sort<T> 实现分析

    System.Array.Sort<T> 是.NET内置的排序方法, 灵活且高效, 大家都学过一些排序算法,比如冒泡排序,插入排序,堆排序等,不过你知道这个方法背后使用了什么排序算法吗? ...

  10. 域名系统-DNS

    域名系统DNS 域名系统DNS(Domain Name System)是互联网使用的命名系统,用来把便于人们使用的机器名转化为IP地址,域名系统就是名字系统. 很多应用层的软件经常直接使用DNS.DN ...