LeetCode:208. 实现 Trie (前缀树)

208. 实现 Trie (前缀树)

实现一个 Trie (前缀树),包含 insert, search, 和 startsWith 这三个操作。

示例:

Trie trie = new Trie();

trie.insert("apple");
trie.search("apple");   // 返回 true
trie.search("app");     // 返回 false
trie.startsWith("app"); // 返回 true
trie.insert("app");   
trie.search("app");     // 返回 true
说明:

你可以假设所有的输入都是由小写字母 a-z 构成的。
保证所有输入均为非空字符串。

链接:https://leetcode-cn.com/problems/implement-trie-prefix-tree

思路:参考:LeetCode题解

时间复杂度:O(m)  其中 m 为键长,在算法的每次迭代中,我们要么检查要么创建一个节点,直到到达键尾。只需要 m 次操作

空间复杂度:O(m)  最坏的情况下,新插入的键和 Trie 树中已有的键没有公共前缀。此时需要添加 m 个结点,使用 O(m) 空间。

class Trie {
private:
    bool isEnd;
    Trie* next[26];
public:
    /** Initialize your data structure here. */
    Trie() {
        isEnd = false;
        memset(next, 0, sizeof(next));
    }
    
    /** Inserts a word into the trie. */
    void insert(string word) {
        // 存在->匹配   不存在->开辟新节点  另外结束时,加结束标志位
        Trie* node = this;
        for (char ch : word) 
        {
            if (node->next[ch - 'a'] == NULL)   // 不存在:新开辟
            {
                node->next[ch - 'a'] = new Trie();
            }
            node = node->next[ch - 'a'];        // 存在,复用
        }
        node->isEnd =true;                      // 加结束标志位
    }
    
    /** Returns if the word is in the trie. */
    bool search(string word) {
        Trie* node = this;
        for (char ch : word) 
        {
            node = node->next[ch - 'a'];
            if (node == NULL)                   // 如果没找到返回false 
            {
                return false;
            }
        }
        return node->isEnd;                     // 找到,返回word的结束标志位true
    }
    
    /** Returns if there is any word in the trie that starts with the given prefix. */
    bool startsWith(string prefix) {
        Trie* node = this;
        for (char ch : prefix)
        {
            node = node->next[ch - 'a'];
            if (node == NULL)
            {
                return false;
            }
        }
        return true;  // 由于仅匹配word前缀prefix,所以遍历不完整个word的结束标志位isEnd=true,故遍历完prefix直接返回true
    }
};

/**
 * Your Trie object will be instantiated and called as such:
 * Trie* obj = new Trie();
 * obj->insert(word);
 * bool param_2 = obj->search(word);
 * bool param_3 = obj->startsWith(prefix);
 */

LeetCode:208. 实现 Trie (前缀树)_第1张图片

你可能感兴趣的:(LeetCode,前缀树)