AcWing:142. 前缀统计(字典树)

给定N个字符串S1,S2SNS1,S2…SN,接下来进行M次询问,每次询问给定一个字符串T,求S1S1~SNSN中有多少个字符串是T的前缀。

输入字符串的总长度不超过106106,仅包含小写字母。

输入格式

第一行输入两个整数N,M。

接下来N行每行输入一个字符串SiSi。

接下来M行每行一个字符串T用以询问。

输出格式

对于每个询问,输出一个整数表示答案。

每个答案占一行。

输入样例:

3 2
ab
bc
abc
abc
efg

输出样例:

2
0
算法:字典树
 
#include <iostream>
#include <cstdio>
#include <cstring>

using namespace std;

const int maxn = 1e6+7;

int tree[maxn][26];
char str[maxn];
int End[maxn];
int tot = 1;

void insert(char *str) {
    int len = strlen(str);
    int root = 1;
    for(int i = 0; i < len; i++) {
        int idx = str[i] - 'a';
        if(tree[root][idx] == 0) {
            tree[root][idx] = ++tot;
        }
        root = tree[root][idx];
    }
    End[root]++;       //记录每个单词的个数
}

int search(char *str) {
    int len = strlen(str);
    int root = 1;
    int ans = 0;
    for(int i = 0; i < len; i++) {
        int idx = str[i] - 'a';
        if(tree[root][idx] == 0) {
            break;
        }
        root = tree[root][idx];
        ans += End[root];
    }
    return ans;
}

int main() {
    int n, m;
    scanf("%d %d", &n, &m);
    for(int i = 0; i < n; i++) {
        scanf("%s", str);
        insert(str);
    }
    while(m--) {
        scanf("%s", str);
        printf("%d\n", search(str));
    }
    return 0;
}

 

posted @ 2019-08-05 21:23  不会fly的pig  阅读(193)  评论(0编辑  收藏  举报