zoukankan      html  css  js  c++  java
  • USACO Name That Number (dfs+字典树)

    题目大意:2到9每个数字对应3字母(对应关系题中已给出),给定一个长度不超过12的数字序列,则可以对应到多个字符串,现给定一个字典(含很多字符串的文件),打印数字序列对应的且在字典中出现过的字符串。

    分析:每个数字对应3个字母,最坏情况下有12个数字,可对应312=531441个字符串,而且题中字典中的字符串是按字典序给出的,所以可以用二分查找,所以应该可以用暴力+二分过。另一个办法就是建字典树,然后dfs时边搜遍判断,这样效率应该有所提升。我是用字典树过的。

    需要注意的是当字典中不存在符合要求的字符串时,要输出“NONE”

    View Code
    /*
    ID: lijian42
    LANG: C++
    TASK: namenum
    */
    #include <stdio.h>
    #include <string.h>
    #define N 5001
    #define LEN 15
    int node;
    int next[N*LEN][26];
    bool isend[N*LEN];
    int n;
    char num[LEN];
    char name[LEN];
    char table[10][3];
    bool success;
    void add(int cur,int k)
    {
        memset(next[node],0,sizeof(next[node]));
        isend[node]=false;
        next[cur][k]=node++;
    }
    void build()
    {
        FILE *fp=fopen("dict.txt","r");
    
        int i,k,cur;
        char s[LEN];
        node=1;
        memset(next[0],0,sizeof(next[0]));
        while(~fscanf(fp,"%s",s))
        {
            cur=0;
            for(i=0;s[i];i++)
            {
                k=s[i]-'A';
                if(next[cur][k]==0) add(cur,k);
                cur=next[cur][k];
            }
            isend[cur]=true;
        }
    }
    void init()
    {
        int i,j;
        char c='A';
        for(i=2;i<10;i++)
        {
            for(j=0;j<3;j++)
            {
                table[i][j]=c;
                c++;
                if(c=='Q')  c++;
            }
        }
        build();
    }
    void dfs(int dep,int cur)
    {
        if(dep==n)
        {
            name[dep]=0;
            if(isend[cur]) puts(name),success=true;
            return;
        }
        int i=num[dep]-'0',j,k;
        for(j=0;j<3;j++)
        {
            k=table[i][j]-'A';
            if(next[cur][k]==0) continue;
            name[dep]=k+'A';
            dfs(dep+1,next[cur][k]);
        }
    }
    int main()
    {
        freopen("namenum.in","r",stdin);
        freopen("namenum.out","w",stdout);
        init();
        while(~scanf("%s",num))
        {
            n=strlen(num);
            success=false;
            dfs(0,0);
            if(success==false)  puts("NONE");
        }
        return 0;
    }
  • 相关阅读:
    P1128 [HNOI2001]求正整数
    zabbix-server端监控MySQL服务
    对服务器磁盘、CPU、内存使用状态,设置163邮件告警
    JDK8 的FullGC 之 metaspace
    JDK8-废弃永久代(PermGen)迎来元空间(Metaspace)
    JVM的方法区和永久带是什么关系?
    如何使用start with connect by prior递归用法
    JVM原理讲解和调优
    jvm 性能调优工具之 jstat
    记一次HBase内存泄漏导致RegionServer挂掉问题
  • 原文地址:https://www.cnblogs.com/algorithms/p/2604026.html
Copyright © 2011-2022 走看看