leetcode——Add and Search Word - Data structure design

Add and Search Word – Data structure design

Design a data structure that supports the following two operations:

void addWord(word)
bool search(word)

search(word) can search a literal word or a regular expression string containing only letters a-z or .. A . means it can represent any one letter.

For example:

addWord("bad")
addWord("dad")
addWord("mad")
search("pad") -> false
search("bad") -> true
search(".ad") -> true
search("b..") -> true

解题思路

显然需要实现一棵trie树来存储所有的word,而查找word的过程,就是对trie树节点的遍历。

考虑到字符’.’代表任意字符,所以需要遍历当前trie树节点的所有子节点。

为了节约内存开销,采用bit位来表示当前节点所包含的字符。例如:

0001  ->  ‘a’

0010  ->  ‘b’

0101  ->  ‘ca’


java代码

public class WordDictionary {
    Node dict = new Node();
    boolean existNull = false;  // 是否存在 word == null
    boolean existBlankWord = false; // 是否存在 word == ""
    
    static class Node{
        int vals = 0;   // vals的 0-26位,分别代表'a'-'z'字符是否存在。
        int ends = 0;   // ends的 0-26位,分别代表是否存在word以'a'-'z'字符结尾。
        Node[] subs = new Node[26]; // 子节点
    }
    
    // Adds a word into the data structure.
    public void addWord(String word) {
        if(word == null){
            existNull = true;
            return;
        }
        if("".equals(word)){
            existBlankWord = true;
            return;
        }
        addWord(word,0, dict);
    }
    
    private void addWord(String word, int pos, Node node) {
        if( pos >= word.length())
            return;
        int v = word.charAt(pos) - 'a';
        node.vals |= (1<<v);
        if(pos == word.length()-1){
            node.ends |= (1<<v);
        }
        if(node.subs[v] == null){
            node.subs[v] = new Node();
        }
        addWord(word, pos+1, node.subs[v]);
    }

    // Returns if the word is in the data structure. A word could
    // contain the dot character '.' to represent any one letter.
    public boolean search(String word) {
        if(word == null)
            return existNull;
        if("".equals(word)){
            return existBlankWord;
        }
        return search(word, 0, dict);
    }
    
    private boolean search(String word, int pos, Node node){
        if(node == null){
            return false;
        }
        char ch = word.charAt(pos);
        if(pos == word.length()-1){
            if(ch == '.'){
                return node.ends != 0;
            }else{
                int v = ch - 'a';
                return (node.ends & (1<<v)) != 0;
            }
        }
        if(ch == '.'){
            int vals = node.vals;
            for(int i=0; i<26; i++){
                if((vals & (1<<i)) != 0 && search(word, pos+1, node.subs[i]))
                    return true;
            }
            return false;
        }else{
            int v = ch - 'a';
            if((node.vals & (1<<v)) == 0)
                return false;
            else
                return search(word, pos+1, node.subs[v]);
        }
    }
}

// Your WordDictionary object will be instantiated and called as such:
// WordDictionary wordDictionary = new WordDictionary();
// wordDictionary.addWord("word");
// wordDictionary.search("pattern");

点赞