HDU1251 统计难题

来源:互联网 发布:美国黑人矛盾 知乎 编辑:程序博客网 时间:2024/05/16 01:29

一. 原题链接:http://acm.hdu.edu.cn/showproblem.php?pid=1251

二. 题目大意:给若干个单词,做为字典。再给出若干前缀,问每个前缀分别在字典的单词中出现多少次。

三. 思路:字典树模板题。所谓字典树,按本题来说,

1.首先有一个没有存信息的root,每个节点有26(字符集个数)个儿子。

2.插入操作:给一个单词,从第一个字符开始,依次从根节点开始,如果不存在此字符,新建一个新节点,否则,节点的计数域加1,循环一直到单词最后一个字符。

3.查询操作:给一个前缀,从第一个字符开始,依次从根节点开始,如果不存在,返回0,否则,查询完毕返回计数域中的数。

四.代码:

#include <cstdio>#include <cstring>using namespace std;const int MAX_N = 26;const int INF = 0x3f3f3f3f;struct node{    int cnt;    node* next[MAX_N];}heap[500000], root;int top;node *newNode(){    return &heap[top++];}void addNode(char *str){    int len = strlen(str), i;    node *p = &root, *q;    for(i = 0; i < len; i++){        int key = str[i] - 'a';        if(p->next[key] == NULL){            q = newNode();            q->cnt = 1;            memset(q->next, 0, sizeof(q->next));            p->next[key] = q;            p = p->next[key];        }        else{            p = p->next[key];            p->cnt++;        }    }}int Find(char *str){    node *p = &root;    int i, key;    for(i = 0; str[i]; i++){        key = str[i]-'a';        if(p->next[key] == NULL)            return 0;        p = p->next[key];    }    return p->cnt;}int main(){    //freopen("in.txt", "r", stdin);    char tmp[12];    while(gets(tmp) && tmp[0])        addNode(tmp);    while(~scanf("%s", tmp))        printf("%d\n", Find(tmp));    return 0;}


0 0
原创粉丝点击