设计一个包含下面两个操作的数据结构:addWord(word), search(word)
addWord(word)会在数据结构中添加一个单词。而search(word)则支持普通的单词查询或是只包含.和a-z的简易正则表达式的查询。
一个 . 可以代表一个任何的字母。
样例
样例 1:
输入:
addWord("a")
search(".")
输出:
true
样例 2:
输入:
addWord("bad")
addWord("dad")
addWord("mad")
search("pad")
search("bad")
search(".ad")
search("b..")
输出:
false
true
true
true
注意事项
你可以认为所有的单词都只包含小写字母 a-z。
解题思路1:
与Lintcode 442. 实现 Trie(前缀树)类似。不同的是增加了对于‘.’正则表达式的处理,需要搜索每一个可能性,循环方法
public class WordDictionary {
private class Node{
public boolean isWord; //说明以当前节点为尾的字符串能否组成一个单词
public Map<Character, Node> next; //next用map存储连接当前节点的下一个节点的值的集合
public Node(boolean isWord){
this.isWord = isWord;
this.next = new HashMap<>();
}
public Node(){
this(false);
}
}
private Node root;
public WordDictionary(){
root = new Node();
}
/*
* @param word: Adds a word into the data structure.
* @return: nothing
*/
public void addWord(String word) {
// write your code here
Node cur = root;
for(int i=0; i<word.length(); i++){
char c = word.charAt(i);
if(cur.next.get(c) == null)
cur.next.put(c, new Node());
cur = cur.next.get(c);
}
cur.isWord = true;
}
/*
* @param word: A word could contain the dot character '.' to represent any one letter.
* @return: if the word is in the data structure.
*/
public boolean search(String word) {
// write your code here
Node cur = root;
for(int i=0; i<word.length(); i++){
char c = word.charAt(i);
if(c == '.'){
//处理正则表达式,需搜索当前节点的next中的每一种可能性
for(Character ch : cur.next.keySet()){
if(search(word.substring(0,i) + ch + word.substring(i+1)))
return true;
}
return false;
}
if(cur.next.get(c) == null)
return false;
cur = cur.next.get(c);
}
return cur.isWord;
}
}
解题思路2:
递归方法。
public class WordDictionary {
private class Node{
public boolean isWord; //说明以当前节点为尾的字符串能否组成一个单词
public Map<Character, Node> next; //next用map存储连接当前节点的下一个节点的值的集合
public Node(boolean isWord){
this.isWord = isWord;
this.next = new HashMap<>();
}
public Node(){
this(false);
}
}
private Node root;
public WordDictionary(){
root = new Node();
}
/*
* @param word: Adds a word into the data structure.
* @return: nothing
*/
public void addWord(String word) {
// write your code here
Node cur = root;
for(int i=0; i<word.length(); i++){
char c = word.charAt(i);
if(cur.next.get(c) == null)
cur.next.put(c, new Node());
cur = cur.next.get(c);
}
cur.isWord = true;
}
/*
* @param word: A word could contain the dot character '.' to represent any one letter.
* @return: if the word is in the data structure.
*/
public boolean search(String word) {
// write your code here
return match(root, word, 0);
}
//考察word中从index开始的字符串是否匹配以node为根的next节点
private boolean match(Node node, String word, int index){
if(index > word.length())
return false;
if(index == word.length())
return node.isWord;
char c = word.charAt(index);
if(c != '.'){
if(node.next.get(c) == null)
return false;
return match(node.next.get(c), word, index+1);
}else{ //c == '.'
for(Character ch : node.next.keySet()){
if(match(node.next.get(ch), word, index+1))
return true;
}
return false;
}
}
}

491

被折叠的 条评论
为什么被折叠?



