HDU-1251-统计难题(字典树||map)

来源:互联网 发布:宏观经济信息数据库 编辑:程序博客网 时间:2024/05/18 17:59

统计难题

Time Limit: 4000/2000 MS (Java/Others) Memory Limit: 131070/65535 K (Java/Others)
Total Submission(s): 35729 Accepted Submission(s): 13363

Problem Description
Ignatius最近遇到一个难题,老师交给他很多单词(只有小写字母组成,不会有重复的单词出现),现在老师要他统计出以某个字符串为前缀的单词数量(单词本身也是自己的前缀).

Input
输入数据的第一部分是一张单词表,每行一个单词,单词的长度不超过10,它们代表的是老师交给Ignatius统计的单词,一个空行代表单词表的结束.第二部分是一连串的提问,每行一个提问,每个提问都是一个字符串.

注意:本题只有一组测试数据,处理到文件结束.

Output
对于每个提问,给出以该字符串为前缀的单词的数量.

Sample Input
banana
band
bee
absolute
acm

ba
b
band
abc

Sample Output
2
3
1
0

字典树模板来一发(G++超内存,交C++78ms)

#include<stdio.h>#include<string.h>#include<iostream>#include<algorithm>using namespace std;const int maxn=555555;struct node{    node *ch[26];    int num;};node a[maxn],*root;char s[11];int p=0;node *newnode(){    memset(a[p].ch,0,sizeof(a[p].ch));    a[p].num=0;    return &a[p++];}void Insert(char *s){    node *cur=root;    cur->num++;    while(*s!='\0')    {        int t=*(s++)-'a';        if(cur->ch[t]==NULL)            cur->ch[t]=newnode();        cur=cur->ch[t];        cur->num++;    }}int getans(char *s){    node *cur=root;    while(*s!='\0')    {        int t=*(s++)-'a';        if(cur->ch[t]==NULL)            return 0;        cur=cur->ch[t];    }    return cur->num;}int main(){    root=newnode();    gets(s);    while(s[0]!='\0')    {        Insert(s);        gets(s);    }    while(scanf("%s",s)!=EOF)    {        printf("%d\n",getans(s));    }    return 0;}

暴力map来一发(904ms)

#include<stdio.h>#include<iostream>#include<algorithm>#include<string.h>#include<map>using namespace std;const int maxn=12;int main(){    map<string,int>m;    char str[maxn];    while(gets(str))    {        int len=strlen(str);        if(!len)            break;        for(int i=len;i>0;i--)        {            str[i]='\0';            m[str]++;        }    }    while(gets(str))    {        printf("%d\n",m[str]);    }    return 0;}

动态分配内存的字典树

//字典树模板#include<stdio.h>#include<iostream>#include<algorithm>#include<string.h>#include<malloc.h>using namespace std;const int maxn=27;struct Trie{    Trie *next[maxn];    int num;};Trie root;//根节点void InsertTrie(char *str){     int len=strlen(str);     Trie *p=&root;     Trie *q;     for(int i=0;i<len;i++)     {         int point=str[i]-'a';         if(p->next[point]==NULL)         {             q=(Trie *)malloc(sizeof(root));             q->num=1;             for(int j=0;j<maxn;j++)                q->next[j]=NULL;             p->next[point]=q;         }         else             p->next[point]->num++;         p=p->next[point];     }}int FindResult(char *str){    Trie *p=&root;    int len=strlen(str);    for(int i=0;i<len;i++)    {        int point=str[i]-'a';        if(p->next[point]==NULL)            return 0;        p=p->next[point];    }    return p->num;}int main(){    for(int i=0; i<maxn; i++)        root.next[i]=NULL;    char str[maxn];    memset(str,'\0',sizeof(str));    while(gets(str)&&str[0]!='\0')        InsertTrie(str);    memset(str,'\0',sizeof(str));    while(scanf("%s",str)!=EOF)        printf("%d\n",FindResult(str));    return 0;}
0 0
原创粉丝点击