• Codeforces 852G Bathroom terminal 【Trie树】


    <题目链接>

    题目大意:

    现在给定出n个字符串,并且进行m此询问,每次询问给出一个匹配串,每次询问都给出该匹配串能够匹配的字符串个数(题目只出现字符'a'~'e')。'?'可以看成任意字符,也可以看做没有。

    解题分析:

    对这n个字符串建立Trie树,然后对每次输入的匹配串在trie树上进行模糊匹配,'?'的分类匹配主要体现在Trie树上的DFS过程。

    #include<bits/stdc++.h>
    using namespace std;
    
    const int M = 55;
    const int N = 1e5+7;
    int nxt[N*M][5], val[N*M], flag[N*M];
    char s[M], str[M];
    int n, m, size = 1;
    
    void insert(char *s){
        int now = 1;
        for (int i=0; s[i]; i++){
            int to=s[i]-'a';
            if (!nxt[now][to]) nxt[now][to] = ++size;
            now = nxt[now][to];
        }
        val[now]++;
    }
    
    int dfs(int loc, int now){   //u为trie树上的节点编号
        if (!now) return 0;           
        if (!str[loc]){      
            if (flag[now] == m+1) return 0;    //Trie树上的同一字符串是否只匹配一次(因为下面进行了多次模糊匹配选择,可能会发生重复
            else{
                flag[now] = m+1;
                return val[now];
            }
        }
        if (str[loc] != '?') return dfs(loc+1, nxt[now][str[loc]-'a']);     //如果当前字符匹配成功
        //对于匹配串中为'?'字符的,具有以下两种选择
        int res = dfs(loc+1, now);      //跳过匹配串中'?'的位置
        for (int i=0; i<5; i++)     //将'?'作为任意字符串,与Trie树上的字符进行匹配
            res += dfs(loc+1, nxt[now][i]);
        return res;
    }
    
    int main(){
        scanf("%d%d", &n, &m);getchar();
        for (int i=1; i<=n; i++){
            gets(s);
            insert(s);
        }
        while (m--){
            gets(str);
            printf("%d
    ", dfs(0, 1));
        }
    }

    2019-02-22

  • 相关阅读:
    第二次实验课总结
    第一次实验课总结
    文件操作
    事件监听 计算器界面
    个人信息
    学生成绩管理
    银行管理
    类的抽象与封装
    求最大公约数和最小公倍数
    阶乘
  • 原文地址:https://www.cnblogs.com/00isok/p/10421180.html
Copyright © 2020-2023  润新知