字典树java版本

来源:互联网 发布:韩顺平php入门到精通 编辑:程序博客网 时间:2024/05/19 18:39
package trietree;
/*
 * 字典树的基本数据结构
 * 字典树的性质:
 * 1:根节点无数据
 * 2:除了根节点,每个节点都只有一个元素
 * 3:从根节点到叶节点是一个完成的单词,每一个节点的子节点没有重复的
 * */
public class TrieNode {


private int num;//当前节点出现的次数
private TrieNode[] son;
private boolean ieEnd;
private boolean visited;
private char val;



public TrieNode(char element){
this.num=1;
this.son=new TrieNode[26]; 
this.ieEnd=false;
this.visited=false;
this.val=element;
}
public TrieNode(){
this.num=1;
this.son=new TrieNode[26]; 
this.ieEnd=false;
this.visited=false;
}

public TrieNode(int num, TrieNode[] son, boolean ieEnd, boolean visited,
char val) {
super();
this.num = num;
this.son = son;
this.ieEnd = ieEnd;
this.visited = visited;
this.val = val;
}
public int getNum() {
return num;
}
public void setNum(int num) {
this.num = num;
}
public TrieNode[] getSon() {
return son;
}
public void setSon(TrieNode[] son) {
this.son = son;
}
public boolean isIeEnd() {
return ieEnd;
}
public void setIeEnd(boolean ieEnd) {
this.ieEnd = ieEnd;
}
public boolean isVisited() {
return visited;
}
public void setVisited(boolean visited) {
this.visited = visited;
}
public char getVal() {
return val;
}
public void setVal(char val) {
this.val = val;
}


@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + val;
return result;
}


@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
TrieNode other = (TrieNode) obj;
if (val != other.val)
return false;
return true;
}

}

package trietree;


import java.util.LinkedList;


/*
 * yy
 * 1:字典树的插入
 * 2:查找
 * 3:统计前缀
 * 4:遍历字典树
 * */
public class TrieTree {

private TrieNode root;


public TrieNode getRoot() {
return root;
}


public void setRoot(TrieNode root) {
this.root = root;
}


public TrieTree(TrieNode root) {
super();
this.root = root;
}


public TrieTree() {
      this.root=new TrieNode();
}


//向字典树插入一个字符串
public void insert(String str){
if(str==null||str.equalsIgnoreCase(""))return ;
TrieNode node=this.root;
char[] letters=str.toCharArray();
int len=str.length();
for(int i=0;i<len;i++){
int pos=letters[i]-'a';
if(node.getSon()[pos]==null){
node.getSon()[pos]=new TrieNode(letters[i]);
}else{
node.getSon()[pos].setNum(node.getSon()[pos].getNum()+1);
}
node=node.getSon()[pos];
}
node.setIeEnd(true);
}

//计算给定当前前缀有多少字符串
public int countPrefix(String prefix){
if(prefix==null || "".equalsIgnoreCase(prefix))return -1;
TrieNode node=this.root;
char[] letters=prefix.toCharArray();
int len=prefix.length();
for(int i=0;i<len;i++){
int pos=letters[i]-'a';
if(node.getSon()[pos]==null){
return 0;
}else{
node=node.getSon()[pos];
}
}
return node.getNum();
}

//查看当前的字典树是否包含某个单词
public boolean has(String str){
if(str==null||"".equalsIgnoreCase(str))return false;
TrieNode node=this.root;
char[] letters=str.toCharArray();
int len=str.length();
for(int i=0;i<len;i++){
int pos=letters[i]-'a';
if(node.getSon()[pos]==null){
return false;
}else{
node=node.getSon()[pos];
}
}
return node.isIeEnd();
}

//遍历当前的字典树
public void printALlWords(){
TrieNode rootnode=this.root;
if(rootnode==null)return ;
LinkedList<TrieNode> list=new LinkedList<TrieNode>();
for(int i=0;i<26;i++){
TrieNode node=rootnode.getSon()[i];
if(node!=null){
list.addLast(node);
while(!list.isEmpty()){
TrieNode current=list.getLast();
TrieNode firstChild=firstOfChild(current);
while(firstChild!=null){
list.addLast(firstChild);
firstChild=firstOfChild(firstChild);
}
TrieNode last=list.getLast();
if(last.isIeEnd()==true){
this.printList(list);
}
list.removeLast();
}
}
list.clear();
}
}

//返回当前节点的第一个孩子
private TrieNode firstOfChild(TrieNode current) {
if(current==null)return null;
for(int i=0;i<26;i++){
if(current.getSon()[i]!=null&&current.getSon()[i].isVisited()==false){
current.getSon()[i].setVisited(true);
return current.getSon()[i];
}
}
return null;
}


private void printList(List<TrieNode> list){
if(list==null||list.size()==0)return ;
for(TrieNode node:list){
System.out.print(node.getVal());
}
System.out.println();
}

public static void main(String[] args) {
TrieTree tree=new TrieTree();
String[] strs={"bee","banana", "band","absolute",  "acm"};    // 
String[] prefix={  
           "ba",  
           "b",  
           "band",  
           "abc" 
       };  
   for(String s:strs){
    tree.insert(s);
   }
   for(String pre:prefix){
    System.out.println(pre+":"+tree.countPrefix(pre));
   }
   
   System.out.println(tree.has("banana"));
   System.out.println(tree.has("ba"));
   tree.printALlWords();
}



}

0 0