题目描述
解题思路
题目大意:
给一些电话号码,只要存在其中一个号码是另一个号码的前缀,输出“NO”,否则输出“YES”。
将n个号码插入字典树中,对每个节点维护有多少个号码经过此节点,然后再遍历n个号码,判断前缀是否唯一。
PS:这题用动态分配的Trie写貌似会TLE,从此优先考虑用静态数组的方式写了~~
参考代码
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
struct Trie {
int next[10];
int cnt;
} node[100010];
int num;
void init() {
num = 0;
memset(node, 0, sizeof(node));
}
int getid(char c) { return c - '0'; }
void insert(char* s) {
Trie* head = &node[0];
while (*s) {
int id = getid(*s++);
if (head->next[id] == NULL)
head->next[id] = &node[++num];
head = head->next[id];
(head->cnt)++;
}
}
bool search(char* s) {
Trie* head = &node[0];
while (*s) {
int id = getid(*s++);
head = head->next[id];
}
return (head->cnt) == 1;
}
char phone[10010][11];
int main() {
int T, n;
scanf("%d", &T);
while (T--) {
init();
scanf("%d", &n);
for (int i = 0; i < n; ++i) {
scanf("%s", phone[i]);
insert(phone[i]);
}
bool ok = true;
for (int i = 0; i < n; ++i) {
if (!search(phone[i])) {
ok = false;
break;
}
}
printf("%s\n", ok ? "YES" : "NO");
}
return 0;
}