poj3630—Phone List(字典树)

传送门: 点我
Sample Input
2
3
911
97625999
91125426
5
113
12340
123440
12345
98346
Sample Output
NO
YES
题意:给出一些字符串,判断是否有字符串是另一个字符串的前缀

字典树算法详解:http://blog.csdn.net/piaocoder/article/details/47836559

动态会超时,只能静态建树(188ms)

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define N 100009
int flag1,cnt;
struct TrieNode
{
    int flag;
    TrieNode* Next[10];
} node[N];
char s[N][13];
TrieNode* NewNode()
{
    memset(&node[cnt],0,sizeof(TrieNode));
    return &node[cnt++];
}
int cmp(const void* a,const void* b)//字符串字典序排序
{
    return strcmp((char*)a,(char*)b);
}
void Insert(char* s,TrieNode* p)
{
    if(flag1==1)
        return;
    int len=strlen(s);
    for(int i=0; i<len; i++)
    {
        int j=s[i]-'0';
        if(p->Next[j]==NULL)
            p->Next[j]=NewNode();
        if(p->flag==1)
        {
            flag1=1;
            return ;
        }
        p=p->Next[j];
    }
    p->flag=1;
}
int main()
{
    int t,n,i;
    cin>>t;
    while(t--)
    {
        flag1=0;
        cnt=0;
        scanf("%d",&n);
        TrieNode* root=NewNode();
        for(i=0; i<n; i++)
            scanf("%s",s[i]);
        qsort(s,n,sizeof(s[0]),cmp);//字符串字典序排序
        for(i=0; i<n; i++)
            Insert(s[i],root);
        printf("%s\n",flag1?"NO":"YES");
    }
    return 0;
}

排序水过(313ms):

#include<iostream>
#include<stdio.h>
#include<algorithm>
#include<string>
#define N 10010
using namespace std;
string tel[N];
bool judge(int n)
{
    int i,k,len;
    for(k=0;k<n-1;k++)
    {
        len=tel[k].size();//<tel[k+1].size()?tel[k].size():tel[k+1].size();
        for(i=0;i<len;i++) 
            if(tel[k][i]!=tel[k+1][i])
                break;
        if(i==len) return true;
    }
    return false;
}
int main()
{
    int t,i,n;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d",&n);
        for(i=0;i<n;i++) cin>>tel[i];
        sort(tel,tel+n);
        if(judge(n)) printf("NO\n");
        else printf("YES\n");
    }
    return 0;
}



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值