Java Trie(词典树)实现
实现Trie tree,可用作实现词典。可用来存储,查找及删除string, 同时实现返回前缀为指定字符所有结果的功能。
每个node存所有child节点与及对应path上的字符所组成的map,利用count来记录每个节点的子树种存在多少word,便于删除的操作。
findAllWithPrefix 用到了DFS的思想,遍历所有带有前缀的结果并输出。常见应用于搜索引擎中。
1 class TrieNode { 2 int count; 3 Map<Character, TrieNode> children; 4 boolean isWord; 5 public TrieNode() { 6 count=0; 7 isWord=false; 8 children=new HashMap<Character,TrieNode>(); 9 } 10 } 11 12 public class MyTrie { 13 TrieNode root; 14 15 public MyTrie() { 16 root = new TrieNode(); 17 } 18 19 public boolean search(String s) { 20 if (this.root == null || s == null || s.length() == 0) { 21 return false; 22 } 23 TrieNode cur=root; 24 for (int i = 0; i < s.length(); i++) { 25 TrieNode next=cur.children.get(s.charAt(i)); 26 if(next == null) { 27 return false; 28 } 29 cur=next; 30 } 31 return cur.isWord; 32 } 33 public void insert(String s) { 34 if(search(s) || s == null || s.length() == 0) { 35 return; 36 } 37 TrieNode cur=root; 38 for (int i = 0; i < s.length(); i++) { 39 TrieNode next=cur.children.get(s.charAt(i)); 40 if(next == null) { 41 next=new TrieNode(); 42 cur.children.put(s.charAt(i), next); 43 } 44 cur=next; 45 cur.count++; 46 } 47 cur.isWord=true; 48 } 49 public boolean delete(String s) { 50 if(!search(s)) { 51 return false; 52 } 53 TrieNode cur=root; 54 for(int i=0; i<s.length(); i++) { 55 TrieNode next=cur.children.get(s.charAt(i)); 56 if(next.count == 1) { 57 cur.children.remove(s.charAt(i)); 58 return true; 59 } 60 next.count--; 61 cur=next; 62 } 63 cur.isWord=false; 64 return true; 65 } 66 67 public List<String>findAllWithPrefix(String s){ 68 TrieNode matchNode=searchNode(s); 69 if(matchNode == null) { 70 return null; 71 } 72 List<String>result=new ArrayList<String>(); 73 DFS(result, matchNode, new StringBuilder(s)); 74 return result; 75 } 76 private void DFS(List<String>result, TrieNode matchNode, StringBuilder sb) { 77 if(matchNode.isWord == true) { 78 result.add(sb.toString()); 79 } 80 for(Map.Entry<Character, TrieNode>child : matchNode.children.entrySet()) { 81 sb.append(child.getKey()); 82 DFS(result,child.getValue(),sb); 83 sb.deleteCharAt(sb.length()-1); 84 } 85 } 86 private TrieNode searchNode(String s) { 87 if(s == null || s.length() == 0) { 88 return null; 89 } 90 TrieNode cur=root; 91 for(int i=0; i<s.length(); i++) { 92 TrieNode next=cur.children.get(s.charAt(i)); 93 if(next == null) { 94 return cur; 95 } 96 cur=next; 97 } 98 return cur; 99 } 100 }