Problem Description
度熊手上有一本神奇的字典,你可以在它里面做如下三个操作:
1、insert : 往神奇字典中插入一个单词
2、delete: 在神奇字典中删除所有前缀等于给定字符串的单词
3、search: 查询是否在神奇字典中有一个字符串的前缀等于给定的字符串
Input
这里仅有一组测试数据。第一行输入一个正整数N(1≤N≤100000)N (1\leq N\leq 100000)N(1≤N≤100000),代表度熊对于字典的操作次数,接下来NNN行,每行包含两个字符串,中间中用空格隔开。第一个字符串代表了相关的操作(包括: insert, delete 或者 search)。第二个字符串代表了相关操作后指定的那个字符串,第二个字符串的长度不会超过30。第二个字符串仅由小写字母组成。
Output
对于每一个search 操作,如果在度熊的字典中存在给定的字符串为前缀的单词,则输出Yes 否则输出 No。
Sample Input
5
insert hello
insert hehe
search h
delete he
search hello
Sample Output
Yes
No
package erChaShu;
import java.util.HashMap;
import java.util.Map;
import java.util.Scanner;
//二叉树实现插入 查找 删除
/*
1、insert : 往神奇字典中插入一个单词
2、delete: 在神奇字典中删除所有前缀等于给定字符串的单词
3、search: 查询是否在神奇字典中有一个字符串的前缀等于给定的字符串
InPut输入数据样例:
5 //代表接下来的操作次数
insert hello //insert 插入 hello 这个单词
insert hehe //insert 插入 hehe 这个单词
search h // search 查找 h 开头的单词
delete he // delete 删除 以 he 为前缀的单词
search hello // searcch 查找 hello 为前缀的单词
*
*
*
*
*
*
* */
//用TrieTree 来解决本题
public class Main {
Word root = new Word('@');// 总目录,它的子节点为词典所有单词的首字母
public static void main(String args[]) {
Main m = new Main();
m.getInput();
}
public void getInput() {
Scanner cin = new Scanner(System.in);
while (cin.hasNext()) {
int N = cin.nextInt();
for (int i = 0; i < N; i++) {
String option = cin.next();// 操作,用String来保存
String str = cin.nextLine();// 单词,用String来保存
Order(option, str);
}
break;
}
cin.close();
}
// 根据输入,找到对应的命令:insert,delete,search
public void Order(String opt, String str) {
char[] charArray = str.toCharArray();// 将单词字符串转化为字符数组
switch (opt) {
case "insert": {
insertTrieTree(charArray);
break;
}
case "delete": {
delTrieTree(charArray);
break;
}
case "search": {
searchTrieTree(charArray);
break;
}
default: {
// System.out.println();
break;
}
}
}
// 删除操作 delete str:删除以str为前缀的“单词”
public void delTrieTree(char[] cc) {
int count = 0;
Word pa = root;
if (root.ch.containsKey(cc[0])) {
Word w = root.ch.get(cc[0]);
int i = 0;
for (i = 1; i < cc.length; i++) {
if (w.ch.containsKey(cc[i])) {
pa = w;
w = w.ch.get(cc[i]);
} else
break;
}
if (i == cc.length) {
count = w.num;
pa.ch.remove(cc[i - 1]);
w.ch.clear();
w = root.ch.get(cc[0]);
for (i = 1; i < cc.length; i++) {
w.num -= count;
w = w.ch.get(cc[i]);
}
}
}
}
// 查找
public void searchTrieTree(char[] cc) {
if (root.ch.containsKey(cc[0])) {
Word w = root.ch.get(cc[0]);
int i = 0;
for (i = 1; i < cc.length; i++) {
if (w.ch.containsKey(cc[i])) {
w = w.ch.get(cc[i]);
} else
break;
}
if (i == cc.length && w.num > 0)
System.out.println("Yes");
else
System.out.println("No");
} else
System.out.println("No");
}
// 插入
public void insertTrieTree(char[] cc) {
if (!root.ch.containsKey(cc[0])) {
root.ch.put(cc[0], new Word(cc[0]));
}
root.ch.get(cc[0]).num++;
Word w = root.ch.get(cc[0]);
for (int i = 1; i < cc.length; i++) {
if (!w.ch.containsKey(cc[i])) {
w.ch.put(cc[i], new Word(cc[i]));
}
w = w.ch.get(cc[i]);
w.num++;
}
}
}
class Word {
char c;
int num = 0;
public Word(char c) {
this.c = c;
}
Map<Character, Word> ch = new HashMap<Character, Word>();
}