Phone list(Trie树模板)

 

Phone List

共t组数据,给定n个长度不超过10的字符串,问其中是否存在两个数S,T,使得S是T的前缀。

存在则输出NO,不存在输出YES

 

输入样例#1:
2
3
911
97625999
91125426
5
113
12340
123440
12345
98346
输出样例#1:
NO
YES
此题转自洛谷UVA11362

Trie树模板题,可以一边构建Trie树一边判断答案,详见代码。
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<cmath>
using namespace std;

inline int read()
{
    int f=1,x=0;
    char ch=getchar();
    while(ch<'0' || ch>'9') {if(ch=='-') f=-1; ch=getchar();}
    while(ch>='0' && ch<='9') {x=x*10+ch-'0'; ch=getchar();}
    return x*f;
}

int T,n,cnt=1;
bool flag;
int ove[100005],pre[100005],tree[100005][15];
char a[100005];
/*
tree是trie树
ove[i]表示以i为结点的数
pre[i]表示i结点的出边数 
*/
void insert(char *s)//插入+查找 
{
    int len=strlen(s),p=1;
    for(int i=0;i<len;i++)
    {
        int c=s[i]-'0';//若是字母串,变为-'a' 
        if(tree[p][c]==0)//若当前结点p的子节点中没有要找的c,则将c插入 
            tree[p][c]=++cnt; 
        p=tree[p][c];//继续查找 
        pre[p]++;
        if(ove[p])//某串是该串的前缀 
        {
            flag=1;
            break;
        }
    }
    ove[p]=1;//标记该串在结点p结束 
    if(pre[p]>1)//该串是某串的前缀 
        flag=1;
}

int main()
{
    T=read();
    int i,j;
    while(T--)
    {
        memset(tree,0,sizeof(tree));
        memset(ove,0,sizeof(ove));
        memset(pre,0,sizeof(pre));
        flag=0;
        cnt=1;
        n=read();
        for(i=1;i<=n;i++)
        {
            scanf("%s",a);
            if(!flag)
                insert(a);
        }
        if(flag)
            printf("NO\n");
        else
            printf("YES\n");
    }
    return 0;
}
这是代码

 

 
posted @ 2018-07-25 15:49  白驹过隙----青春绿  Views(334)  Comments(0Edit  收藏  举报