[luogu2292][L语言]
思路
这道题我用的是AC自动机的做法。
先把子串挂到trie树上,在单词结尾打标记的时候,标记的是当前单词的长度。然后去上面查询母串的时候,每查询到一个单词,就建立一条线段,这条线段的结尾位置是母串当前的位置,开始位置就是用当前位置减去这个单词的长度。
然后只要去判断,选出一些线段,使得这些线段紧挨着(既不相互覆盖,中间也不遗漏)从母串开始位置铺,能铺到的最远的地方。所以只需要一遍bfs就行了。
代码
/*
* @Author: wxyww
* @Date: 2018-12-17 08:38:38
* @Last Modified time: 2018-12-17 09:09:28
*/
#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<bitset>
#include<cstring>
#include<queue>
using namespace std;
typedef long long ll;
const int N = 2000000 + 100;
ll read() {
ll x=0,f=1;char c=getchar();
while(c<'0'||c>'9') {
if(c=='-') f=-1;
c=getchar();
}
while(c>='0'&&c<='9') {
x=x*10+c-'0';
c=getchar();
}
return x*f;
}
int trie[1000][30],end[1000];
char s[30];
int tot;
void insert() {
int len = strlen(s + 1);
int now = 0;
for(int i = 1;i <= len;++i) {
int k = s[i] - 'a';
if(!trie[now][k]) trie[now][k] = ++tot;
now = trie[now][k];
}
end[now] = len;
}
struct node {
int l,r;
}e[N];
int ejs;
int fail[N];
char S[N];
queue<int>q;
void build() {
for(int i = 0;i < 26;++i) if(trie[0][i]) q.push(trie[0][i]);
while(!q.empty()) {
int u = q.front();q.pop();
for(int i = 0;i < 26;++i) {
if(trie[u][i]) fail[trie[u][i]] = trie[fail[u]][i],q.push(trie[u][i]);
else trie[u][i] = trie[fail[u]][i];
}
}
}
vector<int>v[N];
void work() {
int len = strlen(S + 1);
ejs = 0;int now = 0;
for(int i = 1;i <= len;++i) {
now = trie[now][S[i] - 'a'];
for(int j = now;j;j = fail[j]) {
if(end[j]) e[++ejs].l = i - end[j] + 1,e[ejs].r = i;
}
}
}
int vis[N];
void bfs() {
q.push(1);
int ans = 0;
for(int i = 1;i <= ejs;++i) v[e[i].l].push_back(i);
memset(vis,0,sizeof(vis));
while(!q.empty()) {
int l = q.front();q.pop();
int k = v[l].size();
for(int i = 0;i < k;++i) {
int z = v[l][i];
if(vis[z]) continue;
vis[z] = 1;
q.push(e[z].r + 1);
ans = max(ans,e[z].r);
}
}
printf("%d\n",ans);
int len = strlen(S + 1);
for(int i = 1;i <= len;++i) v[i].clear();
}
int main() {
int n = read(),m = read();
for(int i = 1;i <= n;++i) {
scanf("%s",s + 1);
insert();
}
build();
for(int i = 1;i <= m;++i) {
scanf("%s",S + 1);
work();
bfs();
}
return 0;
}
[luogu2292][L语言]的更多相关文章
- BZOJ 1212: [HNOI2004]L语言 [AC自动机 DP]
1212: [HNOI2004]L语言 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 1367 Solved: 598[Submit][Status ...
- 【BZOJ1212】[HNOI2004]L语言 Trie树
[BZOJ1212][HNOI2004]L语言 Description 标点符号的出现晚于文字的出现,所以以前的语言都是没有标点的.现在你要处理的就是一段没有标点的文章. 一段文章T是由若干小写字母构 ...
- BZOJ 1212: [HNOI2004]L语言( dp + trie )
因为单词很短...用trie然后每次dp暴力查找...用哈希+dp应该也是可以的.... ------------------------------------------------------- ...
- [HNOI2004]Language L语言
2777: [HNOI2004]Language L语言 Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 10 Solved: 5[Submit][S ...
- 1212: [HNOI2004]L语言
1212: [HNOI2004]L语言 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 643 Solved: 252[Submit][Status] ...
- 【BZOJ1212】L语言(AC自动机)
[BZOJ1212]L语言(AC自动机) 题面 BZOJ 题解 很自然的,既然要匹配单词,那就全部都丢到\(AC\)自动机里面去 现在想想怎么匹配 先是\(AC\)自动机正常的匹配 如果此时这个位置能 ...
- BZOJ_1212_[HNOI2004]L语言_哈希
BZOJ_1212_[HNOI2004]L语言_哈希 Description 标点符号的出现晚于文字的出现,所以以前的语言都是没有标点的.现在你要处理的就是一段没有标点的文章. 一段文章T是由若干小写 ...
- 洛谷 P2292 [HNOI2004] L语言 解题报告
P2292 [HNOI2004] L语言 题目描述 标点符号的出现晚于文字的出现,所以以前的语言都是没有标点的.现在你要处理的就是一段没有标点的文章. 一段文章\(T\)是由若干小写字母构成.一个单词 ...
- 洛谷:P2292 [HNOI2004]L语言(DP+Trie树)
P2292 [HNOI2004]L语言 题目链接:https://www.luogu.org/problemnew/show/P2292 题目描述 标点符号的出现晚于文字的出现,所以以前的语言都是没有 ...
随机推荐
- git ignore 忽略 idea文件
下载了项目组的代码之后发现,一个问题,一编译就生成了很多的 .idea文件夹 还有 target文件夹,这些是不需要提交到git上的, 需要提交的时候屏蔽一下,所以需要建立一个ignore文件列表把他 ...
- python数据结构与算法第九天【选择排序】
1.选择排序的原理 2.代码实现 def selection_sort(alist): n = len(alist) # 需要进行n-1次选择操作 for i in range(n-1): # 记录最 ...
- QTP 自动化测试--点滴 获取datatable数值/dafault文件位置
0 设置default.xls文件位置 右键项目-settings-resources-datatable-选择 数据表的位置如图 心得:同一个项目-分成多个测试项目-这些测试项目可以共用同一张数据表 ...
- vs code軟件操作
https://www.imooc.com/article/39349 https://www.html.cn/archives/8144
- java 环境变量配置 详解!
<!doctype html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.mybatis.spring.mapper.MapperScannerConfigurer#0'
七月 05, 2018 10:26:54 上午 org.apache.tomcat.util.digester.SetPropertiesRule begin警告: [SetPropertiesRul ...
- <c:forEach>可以默认的把以逗号分隔的字符串作为一个集合来遍历
<c:forEach>可以默认的把以逗号分隔的字符串作为一个集合来遍历
- codeforces570C
Replacement CodeForces - 570C 话说很久很久以前,孙悟空被压在了山下,很无聊.于是他找了一个只包含小写字母和字符"." 的字符串. 由于他比较无聊,他就 ...
- poj2100(尺取法)
题意:选取一系列数,使得这些数的平方和等于n: 解题思路:尺取法扫一遍: #include<iostream> #include<algorithm> using namesp ...
- 【RNN】资源汇总
wesome Recurrent Neural Networks A curated list of resources dedicated to recurrent neural networks ...