题目
鲍勃最近在写论文,为了提升写作效率他需要一款好用的输入法。然而,市面上的输入法大都是为普罗大众准备的,词库中往往没有论文里需要的专有词汇。于是鲍勃决定自己开发一款输入法,帮助自己更高效的完成论文。
输入要求
输入法首先需要构建词库。第一行是一个数字n,代表词库的词数(n ≤ 100000),随后n行内容为n个单词,需要用这些单词构建词库。单词由不超过50个小写字母构成。单词可能重复,词库中重复出现的单词输入法视为同一个单词。
下一行是一个数字q,代表接下来输入法输入q个单词(q ≤10000),随后q行内容为q个单词,代表需要输入的单词。单词由不超过50个小写字母构成。若输入单词不在词库中,且词库中没有以这个单词为前缀的其他单词,这个单词应当被加入词库中。
输出要求
当一个单词被输入后,输入法应将词库中所有以此单词为前缀的单词作为候选词输出。当前单词本身也应作为候选词输出,不论这个词是否在词库中。候选词需按照字典序输出,每个词输出完成后均有一换行。因输入法UI面积有限,每次最多输出50个候选词。
输入
5
too
young
simple
naive
coffee
5
naive
angry
co
covfefe
co
输出
naive
angry
co
coffee
covfefe
co
coffee
covfefe
代码
#include<bits/stdc++.h>
using namespace std;
#define ll long long
struct Tree {
Tree* nxt[26];
bool flag;
Tree() {
memset(nxt,0,sizeof(nxt));
flag = 0;
}
}*root;
int n,q;
char s[110];
int num;
void insert1() {
Tree *rt = root;
int len = strlen(s);
for(int i = 0,x;i < len;++i) {
x = s[i]-'a';
if(rt->nxt[x] == NULL) {
rt->nxt[x] = new Tree();
}
rt = rt->nxt[x];
}
rt->flag = 1;
}
void dfs(int len,Tree *rt) {
if(!num) return;
if(rt->flag == 1) {
s[len] = '\0';
printf("%s\n",s);
if(--num == 0) return;
}
for(int i = 0;i < 26;++i) {
if(rt->nxt[i] != NULL) {
s[len] = 'a'+i;
dfs(len+1,rt->nxt[i]);
if(!num) return;
}
}
}
void find1() {
Tree *rt = root;
int len = strlen(s);
bool f = 1;
for(int i = 0,x;i < len;++i) {
x = s[i]-'a';
if(rt->nxt[x] == NULL) {
rt->nxt[x] = new Tree();
f = 0;
}
rt = rt->nxt[x];
}
printf("%s\n",s);
if(!f)
rt->flag = 1;
else {
num = 49;
for(int i = 0;i < 26;++i) {
if(rt->nxt[i] != NULL) {
s[len] = 'a'+i;
dfs(len+1,rt->nxt[i]);
if(!num) return;
}
}
}
}
int main() {
scanf("%d",&n);
root = new Tree();
for(int i = 0;i < n;++i) {
scanf("%s",s);
insert1();
}
scanf("%d",&q);
while(q--) {
scanf("%s",s);
find1();
}
}