Implement a trie with insert
, search
, and startsWith
methods.
Note:
You may assume that all inputs are consist of lowercase letters a-z
.
Trie树又被称为字典树、前缀树,是一种用于快速检索的多叉树。Tried树可以利用字符串的公共前缀来节省存储空间。
但如果系统存在大量没有公共前缀的字符串,相应的Trie树将非常消耗内存。(下图为Wiki上的Trie树示意图, https://en.wikipedia.org/wiki/Trie)
Trie树的基本性质如下:
- 根节点不包括字符,除根节点外每个节点包括一个支付。
- 从根节点到某一节点,路径上经过的字符连接起来,即为对应的字符串。
- 每个节点的所有子节点包含的字符串各不相同。
本题中的Trie树可以简单实现如下:
Trie树节点数据结构定义如下:
- val表示该节点对应的字符
- 子节点简单用一个数组表示,这样实现比较简单,但比较耗费内存
- isWord标记从根节点到该节点是否表示一个单词,还是另一单词的前缀。
class TrieNode{ public://'TrieNode::TrieNode()' is private within this context char val; bool isWord; TrieNode* children[26]; TrieNode() { val=0; isWord=false; memset(children,NULL,sizeof(children)); } TrieNode(char ch){ val=ch; isWord=false; memset(children,NULL,sizeof(children)); } }; class Trie { public: /** Initialize your data structure here. */ Trie() { root=new TrieNode(); } /** Inserts a word into the trie. */ void insert(string word) { TrieNode*pNode=root; for (int i = 0; i < word.length(); ++i) { char ch=word[i]; if(pNode->children[ch-'a']==NULL) { TrieNode* newNode=new TrieNode(ch); pNode->children[ch-'a']=newNode; pNode=newNode; }else pNode=pNode->children[ch-'a']; } pNode->isWord=true; } /** Returns if the word is in the trie. */ bool search(string word) { TrieNode*pNode=root; for (int i = 0; i < word.length(); ++i) { char ch=word[i]; pNode=pNode->children[ch-'a']; if(pNode==NULL) return false; } return pNode->isWord; } /** Returns if there is any word in the trie that starts with the given prefix. */ bool startsWith(string prefix) { TrieNode*pNode=root; for (int i = 0; i < prefix.length(); ++i) { char ch=prefix[i]; pNode=pNode->children[ch-'a']; if(pNode==NULL) return false; } return true; } void freeAllNode(TrieNode* root) { TrieNode*pNode=root; if(root==NULL) return; for (int i = 0; i < 26; ++i) { TrieNode* pNode=root->children[i]; if(pNode!=NULL)freeAllNode(pNode); } free(pNode); } ~Trie() { freeAllNode(root); } private: TrieNode*root; }; /** * 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); */
注意:1.不需要在孩子节点中遍历寻找是否有等于某个节点的点!!!char ch='k' 一定在指针数组['k'-'a']这个位置上- class默认是“”私有“”继承,struct才是"公开"继承
- 深度优先,遍历递归,free指针时。