Keywords Search HDU - 2222 AC自动机板子题
Wiskey also wants to bring this feature to his image retrieval system.
Every image have a long description, when users type some keywords to find the image, the system will match the keywords with description of image and show the image which the most keywords be matched.
To simplify the problem, giving you a description of image, and some keywords, you should tell me how many keywords will be match.
InputFirst line will contain one integer means how many cases will follow by.
Each case will contain two integers N means the number of keywords and N keywords follow. (N <= 10000)
Each keyword will only contains characters 'a'-'z', and the length will be not longer than 50.
The last line is the description, and the length will be not longer than 1000000.
OutputPrint how many keywords are contained in the description.Sample Input
1
5
she
he
say
shr
her
yasherhs
Sample Output
3
题意:
T组输入,对于每组数据有n个模式串,最后输入一个待求串。让你求这个待求串中有多少种模式串
注意:这个模式串可能会重复,重复的话要算做多个,不能算作一个
代码:
1 /*
2 代码中:
3 叶节点:代表此节点下没有子节点
4 根节点:就是树的根
5 子节点:就是这个节点的直接相连的节点(直系节点)
6
7 此代码:
8 用题目所给模式串构成一颗字典树
9 然后找出来给出的待求串中有多少种模式串(如果模式串中有重复的,那么也算作多个,不算一个)
10
11 */
12 #include<stdio.h>
13 #include<iostream>
14 #include<string.h>
15 #include<algorithm>
16 #include<queue>
17 using namespace std;
18 const int maxn=5e5+10;
19 const int N=26;
20 typedef long long ll;
21 struct Trie
22 {
23 int next[maxn][N],fail[maxn],ends[maxn];
24 int root,L;
25 int New_node() //创建一个新节点
26 {
27 for(int i=0;i<N;++i)
28 {
29 next[L][i]=-1; //每次初始化新节点
30 }
31 ends[L++]=0; //每次初始化新节点
32 return L-1;
33 }
34 void init() //创建根节点
35 {
36 L=0;
37 root=New_node();
38 }
39 void inserts(char s[]) //往字典树里面插入新字符串
40 {
41 int len=strlen(s);
42 int now=root;
43 for(int i=0;i<len;++i)
44 {
45 if(next[now][s[i]-'a']==-1)
46 next[now][s[i]-'a']=New_node();
47 now=next[now][s[i]-'a'];
48 }
49 ends[now]++; //字典树的叶节点要标记,如果走到这个位置就代表这种模式串出现过
50 }
51 void build()
52 {
53 queue<int>r;
54 fail[root]=root;
55 for(int i=0;i<N;++i) //先给字典树根节点下的N个子节点初始化一下
56 {
57 if(next[root][i]==-1) //代表字典树上都没有i这个分支,对于这些节点的下一级就直接指向根节点就完了
58 {
59 next[root][i]=root;
60 }
61 else //字典树上有i这个分支的,就要改变它的fail(即,失败指针)的值
62 {
63 fail[next[root][i]]=root;
64 r.push(next[root][i]);
65 }
66 }
67 while(!r.empty())
68 {
69 int now=r.front();
70 r.pop();
71 for(int i=0;i<N;++i)
72 {
73 if(next[now][i]==-1)
74 {
75 next[now][i]=next[fail[now]][i];
76 //代表now在叶节点处,此时往下一个节点走就直接通过now节点失败指针进行跳转
77 }
78 else
79 {
80 fail[next[now][i]]=next[fail[now]][i]; //此节点的子节点的失败指针就是此节点失败指针对应字符位置
81 r.push(next[now][i]);
82 }
83 }
84 }
85 }
86 int query(char s[])
87 {
88 int len=strlen(s);
89 int now=root;
90 int res=0;
91 for(int i=0;i<len;++i)
92 {
93 now=next[now][s[i]-'a']; //这个now就保证了我们找的肯定是这个s字符串中的一部分
94 int temp=now; //这就是一直找,找到了就加1,找不到就通过失败指针看其他地方能不能找到
95 while(temp!=root) //尝试这个节点的失败指针能不能找到模式串
96 {
97 res+=ends[temp]; //因为我们要找出来s串中包含几种模式串,所以要有赋值0操作
98 ends[temp]=0;
99 temp=fail[temp];
100 }
101 }
102 return res;
103 }
104 };
105 char s[1000010];
106 Trie ac;
107 int main()
108 {
109 int t;
110 scanf("%d",&t);
111 while(t--)
112 {
113 int n;
114 scanf("%d",&n);
115 ac.init();
116 while(n--)
117 {
118 scanf("%s",s); //这个就是模式串
119 ac.inserts(s);
120 }
121 ac.build();
122 scanf("%s",s); //这个是待求串
123 printf("%d\n",ac.query(s));
124 }
125 return 0;
126 }
Keywords Search HDU - 2222 AC自动机板子题的更多相关文章
- hdu 2222(AC自动机模版题)
Keywords Search Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others ...
- HDU 2222 AC自动机模板题
题目: http://acm.hdu.edu.cn/showproblem.php?pid=2222 AC自动机模板题 我现在对AC自动机的理解还一般,就贴一下我参考学习的两篇博客的链接: http: ...
- HDU 2222 AC自动机(模版题)
Keywords Search Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others ...
- HDU 2222 AC自动机 裸题
题意: 问母串中出现多少个模式串 注意ac自动机的节点总数 #include <stdio.h> #include <string.h> #include <queue& ...
- HDU 2222 AC自动机模版题
所学的AC自动机都源于斌哥和昀神的想法. 题意:求目标串中出现了几个模式串. 使用一个int型的end数组记录,查询一次. #include <cstdio> #include <c ...
- AC日记——Keywords Search hdu 2222
2222 思路: ac自动机模板题: 代码: #include <cstdio> #include <cstring> #include <iostream> #i ...
- HDU 3065 (AC自动机模板题)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=3065 题目大意:多个模式串,范围是大写字母.匹配串的字符范围是(0~127).问匹配串中含有哪几种模 ...
- HDU 2896 (AC自动机模板题)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=2896 题目大意:多个模式串.多个匹配串.其中串的字符范围是(0~127).问匹配串中含有哪几个模式串 ...
- HDU-2222 Keywords Search 字符串问题 AC自动机
题目链接:https://cn.vjudge.net/problem/HDU-2222 题意 给一些关键词,和一个待查询的字符串 问这个字符串里包含多少种关键词 思路 AC自动机模版题咯 注意一般情况 ...
随机推荐
- 安装Tomcat 9
文章目录 访问Tomcat官网 选择下载所需的软件包 安装Tomcat 测试安装 访问Tomcat官网 Tomcat官方的下载地址为:https://tomcat.apache.org/downloa ...
- 【Linux】实现端口转发的rinetd
Linux下端口转发一般都使用iptables来实现,使用iptables可以很容易将TCP和UDP端口从防火墙转发到内部主机上.但是如果需要将流量从专用地址转发到不在您当前网络上的机器上,可尝试另一 ...
- kubernets之ReplicaSet
一 介绍RS 1.1 RS与RC在功能上基本上是一摸一样的,因为两者的功能都是用来管控集群内部的pod,并且 两者都具备模版,副本数量以及标签选择器等三要素,区别点在于,RS拥有着更为强大的标 ...
- oracle可传输表空间测试
使用RMAN在恢复表空间的时候,表空间数据文件DBID和恢复数据库的数据文件DBID必须相同 可传输表空间不需要这样,也就是可以快速的把这个表空间插入另一个数据库使用 可传输表空间内的对象必须不依赖与 ...
- VBScript调用winscp,实现sftp操作
最新有一个需求,需要在ssis中调用sftp下载文件,由于服务器上只有framework2.0,并且需要用sqlserver代理调用作业,限制了很多. 首先用的是脚本任务,进程调用winscp.com ...
- ABAP program lines are wider than the internal table
错误详细描述: An exception occurred that is explained in detail below.The exception, which is assigned to ...
- 集成多种协议、用于 USB-A 和 TYPE-C 双端口输出的快充协议芯片IP2726
1. 特性 支持 1A1C 支持 USB-A 和 TYPE-C 双端口输出 单口输出支持全部快充协议 双口同时插入时降压到 5V 快充规格 集成 QC2.0/QC3.0/QC4/QC4+输 ...
- HTML基础复习2
6.表格 6.1建立表格: 表格由<table></table>标签来定义 每行由<tr></tr>来定义,每行被分割为若干单元格,由<td> ...
- GlusterFS分布式存储系统复制集更换故障Brick操作记录
场景: GlusterFS 3节点的复制集,由于磁盘故障,其中一个复制集需要重装系统,所以需要重装glusterfs并将该节点加入glusterfs集群 一. 安装GlusterFS 首先在重装系统节 ...
- Cisco发现协议
CDP Cisco Discovery Protocol: 思科发现协议 是一个提供关于直接相连的交换机.路由器和其它Cisco设备的综合信息的专有工具 CDP 能够发现直接相邻的设备而不管这些设备所 ...