标签:
链接:http://blog.csdn.net/acvay/article/details/47089657
题意 给你一组电话号码 判断其中是否有某个电话是另一个电话的前缀
字典树的基础应用 可以先把所有电话存进Trie 标记每个电话的结束字符 然后再查询每个号码 看中途是否有结束标记 有的话就说明有号码是这个号码的前缀了
实际上 插入完成就能知道是否有号码是另一个号码的前缀了 假设A是B的前缀
若A在B之前插入 那么插入B的时候会遇到A的结束标记
弱A在B之后插入 那么A插入完成之后的结点还有非空的孩子结点
这样就只用在每次插入时判断就行了 可以省掉查询这一步
指针和动态内存分配实现字典更容易些 但在有多组样例的时侯不释放内存会导致MLE 释放内存又要多花费不必要的时间 可能导致TLE 所以用数组实现比较好
#include<cstdio> #include<cstring> using namespace std; const int N = 10005; char tel[N][12]; int trie[N * 10][10], L; bool end[N * 10], flag; void initTrie() { L = 1; memset(trie, 0, sizeof(trie)); memset(end, 0, sizeof(end)); } void _insert(char *s) { int r = 0, i = 0, j; while (s[i]) { if (end[r]) flag = false; j = s[i++] - ‘0‘; if (!trie[r][j]) trie[r][j] = L++; r = trie[r][j]; } for (int i = 0; i < 10; i++) { if (trie[r][i]) flag = 0; end[r] = 1; } } int main() { int T, n; scanf("%d", &T); while (T--) { initTrie(); scanf("%d", &n); flag = true; for (int i = 0; i < n; ++i) { scanf("%s", tel[i]); _insert(tel[i]); } puts(flag ? "YES" : "NO"); } return 0; }
HDU 1671 Phone List (Trie·数组实现)
标签:
原文地址:http://www.cnblogs.com/s1124yy/p/5769423.html