HDU2222_Keywords Search _AC自动机模板题
2017-07-23 23:18
441 查看
题意
给出若干单词和一串字符,问这串字符中出现了给出单词中的几个。思路
AC自动机模板题AC自动机学习资料:
kuangbin大神的blog:http://www.cppblog.com/mythit/archive/2009/04/21/80633.html
包括AC代码中的第二种,也是直接从这里抄过来的
题目链接
http://acm.hdu.edu.cn/showproblem.php?pid=2222AC代码
这里代码有两版,第二个是照抄的kuangbin大神的,第二版稍微进行了一些改动,只是更靠近自己的风格,几乎可以说完全一样。版本一
#include<iostream> #include<cstdio> #include<cstring> using namespace std; const int kind = 26; struct node { node *fail; //fail指针 node *next[kind]; //子节点指针 int count; //当前节点代表的单词个数 node() { fail = NULL; count = 0; memset(next, NULL, sizeof next); } }; node *q[500001]; //队列 int head, tail; //队列的首尾指针 char keyword[51]; //单词表 char str[1000001]; //模式串 void insert(char *str, node *root) //将单词插入字典树中 { node *p = root; int i = 0; while(str[i]) { int index = str[i] - 'a'; if(p->next[index] == NULL) p->next[index] = new node(); p = p->next[index]; i ++; } p->count ++; } void build_ac_automation(node *root) { head = tail = 0; q[head ++] = root; while(head != tail) { node *temp = q[tail ++]; node *p = NULL; for(int i= 0; i&l 4000 t; 26; i++) //线序遍历子树 { if(temp->next[i] != NULL) { p = temp->fail; while(p != NULL) //沿着fail链找到一个与当前位置对应的位置,构造fail链 { if(p->next[i] != NULL) { temp->next[i]->fail = p->next[i]; break; } p = p->fail; } if(p == NULL) temp->next[i]->fail = root; //加边失败,fail指针指向root q[head ++] = temp->next[i]; //子节点入队 } } } } int query(node *root) { int i = 0, cnt = 0, len = strlen(str); node *p = root; while(str[i]) //遍历模式串 { int index = str[i] - 'a'; while(p->next[index] == NULL && p != root) p = p->fail; //沿着fail链找一个能继续匹配的树枝,找到root也要停止 p = p->next[index]; if(p == NULL) p = root; //查找失败,p置为root node *temp = p; //沿着fail链检查是否有单词被构成 while(temp != root && temp->count != -1) //-1表示该单词已经被找过一次了 { cnt += temp->count; temp->count = -1; temp = temp->fail; } i ++; } return cnt; } int main() { int n, t; scanf("%d", &t); while(t --) { node *root = new node(); scanf("%d", &n); getchar(); while(n --) { gets(keyword); insert(keyword, root); } build_ac_automation(root); scanf("%s", str); printf("%d\n", query(root)); } return 0; }
版本二
#include<iostream> #include<cstdio> #include<cstring> using namespace std; const int kind = 26; struct node { node *fail; node *next[kind]; int count; node() { fail = NULL; count = 0; memset(next, NULL, sizeof next); } } *q[500001]; char keyword[51]; char str[1000001]; int head, tail; void insert(char *str, node *root) { node *p = root; int i = 0, index; while(str[i]) { index = str[i] - 'a'; if(p->next[index] == NULL) p->next[index] = new node(); p = p->next[index]; i ++; } p->count ++; } void build_ac_automation(node *root) { int i; root->fail = NULL; q[head ++] = root; while(head != tail) { node *temp = q[tail ++]; node *p = NULL; for(int i= 0; i< 26; i++) { if(temp->next[i] != NULL) { if(temp == root) temp->next[i]->fail = root; else{ p = temp->fail; while(p != NULL) { if(p->next[i] != NULL) { temp->next[i]->fail = p->next[i]; break; } p = p->fail; } if(p == NULL) temp->next[i]->fail = root; } q[head ++] = temp->next[i]; } } } } int query(node *root) { int i = 0, cnt = 0, index, len = strlen(str); node *p = root; while(str[i]) { index = str[i] - 'a'; while(p->next[index] == NULL && p != root) p = p->fail; p = p->next[index]; p = (p == NULL) ? root : p; node *temp = p; while(temp != root && temp->count != -1) { cnt += temp->count; temp->count = -1; temp = temp->fail; } i ++; } return cnt; } int main() { int n, t; scanf("%d", &t); while(t --) { head = tail = 0; node *root = new node(); scanf("%d", &n); getchar(); while(n --) { gets(keyword); insert(keyword, root); } build_ac_automation(root); scanf("%s", str); printf("%d\n", query(root)); } return 0; }
相关文章推荐
- HDU2222 Keywords Search [AC自动机模板]
- HDU2222 Keywords Search [AC自动机模板]
- HDU2222 Keywords Search 【AC自动机模板题】
- HDU2222 Keywords Search(AC自动机模板)
- hdu 2222 Keywords Search(AC自动机模板)
- [AC自动机模板题] HDU 2222 Keywords Search
- HDU 2222 Keywords Search 【AC自动机模板】
- HDU 2222 Keywords Search 【AC自动机模板】
- HDU2222 Keywords Search [AC自动机]
- HDU2222 Keywords Search(AC自动机模板题)
- AC自动机学习小记 Hdu 2222 Keywords Search (模板)
- hdu -2222 Keywords Search(AC自动机模板)
- HDU2222 Keywords Search(AC自动机入门)
- [HDU2222]Keywords Search|AC自动机
- HDU 2222 Keywords Search (AC自动机模板)
- poj 2222 Keywords Search,AC自动机模板题
- HDOJ2222Keywords Search【AC自动机模板题】
- hdu2222 Keywords Search & AC自动机学习小结
- HDOJ 2222 - Keywords Search 更新AC自动机模板...用类来表示
- HDU_2222 Keywords Search 【AC自动机模板题】【动态链表】