题目:https://leetcode.com/problems/implement-trie-prefix-tree/
思路:
前缀树的概念,参考这里。谷歌搜到的,其实有一大把~
判断是否有这么个“儿子”的时候,增加了一个hasEnd布尔值,如果有以这个点为结束的字符则设置成true.
限制:为了实现方便,现在只能存储a-z共26个字符,如果再扩展可以考虑用map来存字符对应的孩子指针。
单词的字符数量为M,插入节点的时间复杂度是O(M)
startWith(..)和search(..)一大半部分可以合并
代码:
class TrieNode { public: bool hasEnd; TrieNode** children; // Initialize your data structure here. TrieNode() { children = NULL; hasEnd = false; } bool hasChild(char c) { if (NULL == children) return false; return !(NULL == children[c - 'a']); } TrieNode* addChild(char c) { if (NULL == children) { children = new TrieNode*[26]; for (int i = 0; i<26; i++) children[i] = NULL; } int pos = c - 'a'; children[pos] = new TrieNode; return children[pos]; } }; class Trie { public: Trie() { root = new TrieNode(); } // Inserts a word into the trie. void insert(string word) { int wordSz = word.size(); char c; TrieNode *currNode = root; for (int i = 0; i<wordSz; i++) { c = word[i]; if (currNode->hasChild(c)) currNode = currNode->children[c - 'a']; else { currNode = currNode->addChild(c); } if (i == wordSz - 1) currNode->hasEnd = true; } } // Returns if the word is in the trie. bool search(string word) { int wordSz = word.size(); char c; TrieNode *currNode = root; for (int i = 0; i<wordSz; i++) { c = word[i]; if (currNode->hasChild(c)) currNode = currNode->children[c - 'a']; else return false; } return currNode->hasEnd; } // Returns if there is any word in the trie // that starts with the given prefix. bool startsWith(string prefix) { int wordSz = prefix.size(); char c; TrieNode *currNode = root; for (int i = 0; i<wordSz; i++) { c = prefix[i]; if (currNode->hasChild(c)) currNode = currNode->children[c - 'a']; else return false; } return true; } private: TrieNode* root; }; // Your Trie object will be instantiated and called as such: // Trie trie; // trie.insert("somestring"); // trie.search("key");