Java tutorial
/* * Copyright (C) 2010 Adam Huang <poisondog@gmail.com> * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package poisondog.tree; import java.util.ArrayList; import java.util.Collection; import java.util.HashSet; import java.util.LinkedList; import java.util.List; import org.apache.commons.lang.builder.HashCodeBuilder; /** * ? * @author Adam Huang <poisondog@gmail.com> */ public class BinaryTree<E> implements Cloneable { private BinaryTree<E> parent; private BinaryTree<E> leftTree; private BinaryTree<E> rightTree; private E data; public static int LeftTree = 0; public static int RightTree = 1; protected BinaryTree() { } /** * ? * @param object */ public BinaryTree(E object) { this.data = object; this.parent = new EmptyTree<E>(); this.leftTree = new EmptyTree<E>(); this.rightTree = new EmptyTree<E>(); } /** * ? * @param left */ public void setLeftTree(BinaryTree<E> left) { leftTree.parent = new EmptyTree<E>(); if (left == null) { leftTree = new EmptyTree<E>(); } else { leftTree = left; leftTree.parent = this; } } /** * ?? * @param right */ public void setRightTree(BinaryTree<E> right) { rightTree.parent = new EmptyTree<E>(); if (right == null) { rightTree = new EmptyTree<E>(); } else { rightTree = right; rightTree.parent = this; } } /** * ?? * @return */ public BinaryTree<E> getLeftTree() { return leftTree; } /** * ??? * @return */ public BinaryTree<E> getRightTree() { return rightTree; } /** * ? * @return */ public E getData() { return data; } /** * * @param data */ public void setData(E data) { this.data = data; } public boolean isEmpty() { return false; } /** * ????enull * @param e * @return */ public BinaryTree<E> find(E e) { for (BinaryTree<E> result : this.preorder()) { if (result.getData().equals(e)) return result; } return null; } public BinaryTree<E> parent() { return parent; } /** * @param temp * @return */ public boolean remove(BinaryTree<E> temp) { BinaryTree<E> parent = temp.parent(); if (parent.isEmpty()) return false; if (parent.getLeftTree().equals(temp)) parent.setLeftTree(new EmptyTree<E>()); else if (parent.getRightTree().equals(temp)) parent.setRightTree(new EmptyTree<E>()); return true; } /** * ???? * @return ?? */ public List<BinaryTree<E>> preorder() { List<BinaryTree<E>> list = new ArrayList<BinaryTree<E>>(); preorder(this, list); return list; } private void preorder(BinaryTree<E> tree, List<BinaryTree<E>> list) { list.add(tree); if (!tree.getLeftTree().isEmpty()) preorder(tree.getLeftTree(), list); if (!tree.getRightTree().isEmpty()) preorder(tree.getRightTree(), list); } /** * ??? * @return ? */ public List<BinaryTree<E>> inorder() { List<BinaryTree<E>> list = new ArrayList<BinaryTree<E>>(); inorder(this, list); return list; } private void inorder(BinaryTree<E> tree, List<BinaryTree<E>> list) { if (!tree.getLeftTree().isEmpty()) inorder(tree.getLeftTree(), list); list.add(tree); if (!tree.getRightTree().isEmpty()) inorder(tree.getRightTree(), list); } /** * ??? * @return ? */ public List<BinaryTree<E>> postorder() { List<BinaryTree<E>> list = new ArrayList<BinaryTree<E>>(); postorder(this, list); return list; } private void postorder(BinaryTree<E> tree, List<BinaryTree<E>> list) { if (!tree.getLeftTree().isEmpty()) postorder(tree.getLeftTree(), list); if (!tree.getRightTree().isEmpty()) postorder(tree.getRightTree(), list); list.add(tree); } /* * @see java.lang.Object#equals(java.lang.Object) */ @Override public boolean equals(Object obj) { if (obj == null) return false; BinaryTree<?> target = (BinaryTree<?>) obj; if (!this.getLeftTree().equals(target.getLeftTree())) return false; if (!this.getRightTree().equals(target.getRightTree())) return false; return this.getData().equals(target.getData()); } /* * @see java.lang.Object#hashCode() */ @Override public int hashCode() { HashCodeBuilder builder = new HashCodeBuilder(); builder.append(this.getLeftTree()); builder.append(this.getRightTree()); builder.append(this.getData()); return builder.toHashCode(); } /* * @see java.lang.Object#clone() */ @Override public BinaryTree<E> clone() { BinaryTree<E> clone = new BinaryTree<E>(data); if (!this.getLeftTree().isEmpty()) { clone.setLeftTree(this.getLeftTree().clone()); } if (!this.getRightTree().isEmpty()) { clone.setRightTree(this.getRightTree().clone()); } return clone; } /** * @return */ public Collection<BinaryTree<E>> noLeftChild() { return noLeftChild(this); } private Collection<BinaryTree<E>> noLeftChild(BinaryTree<E> tree) { LinkedList<BinaryTree<E>> result = new LinkedList<BinaryTree<E>>(); if (tree.getLeftTree().isEmpty()) { result.add(tree); } else { result.addAll(noLeftChild(tree.getLeftTree())); } if (!tree.getRightTree().isEmpty()) { result.addAll(noLeftChild(tree.getRightTree())); } return result; } /** * @return */ public Collection<BinaryTree<E>> noRightChild() { return noRightChild(this); } private Collection<BinaryTree<E>> noRightChild(BinaryTree<E> tree) { LinkedList<BinaryTree<E>> result = new LinkedList<BinaryTree<E>>(); if (tree.getRightTree().isEmpty()) { result.add(tree); } else { result.addAll(noRightChild(tree.getRightTree())); } if (!tree.getLeftTree().isEmpty()) { result.addAll(noRightChild(tree.getLeftTree())); } return result; } /** * @return */ public Collection<BinaryTree<E>> notTwoChildParent() { HashSet<BinaryTree<E>> set = new HashSet<BinaryTree<E>>(); set.addAll(noLeftChild()); set.addAll(noRightChild()); return set; } }