二叉搜索树(Java实现)
Posted GoldArowana &
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了二叉搜索树(Java实现)相关的知识,希望对你有一定的参考价值。
二叉搜索树基本操作
求树中的结点个数 判断节点是否为空 向树中插入新结点key-value 树中是否存在key 返回树中key对应的value值 先序遍历 中序遍历 后续遍历 层序遍历 求树中key最小的结点 求树中key最大的结点 删除树中key最小的结点 删除树中key最大的结点 树中删除一个结点
代码:
/** * @param <Key> 键的泛型 * @param <Value> 值的泛型 */ public class BinarySearchTree<Key extends Comparable<? super Key>, Value> { private class Node { private Key key; // 键,相当于词典里的单词 private Value value; // 值,相当于词典里的解释 private Node left; // 左孩子结点 private Node right;// 右孩子结点 //结点的构造函数 public Node(Key key, Value value) { this.key = key; this.value = value; this.left = null; this.right = null; } // getters and setters public Key getKey() { return key; } public void setKey(Key key) { this.key = key; } public Value getValue() { return value; } public void setValue(Value value) { this.value = value; } public Node getLeft() { return left; } public void setLeft(Node left) { this.left = left; } public Node getRight() { return right; } public void setRight(Node right) { this.right = right; } @Override public String toString() { return "Node{" + "key=" + key + ", value=" + value + ‘}‘; } } private Node root; // 二叉搜索树的根节点 private int size; //二叉搜索树中的结点个数 //树的构造函数 public BinarySearchTree() { this.root = null; this.size = 0; } //求树中的结点个数 public int size() { return this.size; } //判断节点是否为空 public boolean isEmpty() { return this.size == 0; } //以node结点为根的树(子树)中插入key-value private Node insert(Node node, Key key, Value value) { if (node == null) { size++; return new Node(key, value); } else if (node.key.compareTo(key) > 0) { node.setLeft(insert(node.getLeft(), key, value)); } else if (node.key.compareTo(key) < 0) { node.setRight(insert(node.getRight(), key, value)); } else { // 相等的时候 node.value = value; } return node; } //向树中插入新结点key-value public void insert(Key key, Value value) { root = insert(root, key, value); } // node结点为根的树(子树)中是否存在key private boolean contain(Node node, Key key) { if (node == null) { return false; } else if (node.key.compareTo(key) == 0) { return true; } else if (node.key.compareTo(key) > 0) { return contain(node.getLeft(), key); } else { return contain(node.getRight(), key); } } //树中是否存在key public boolean contain(Key key) { return contain(root, key); } //返回node结点为根的树(子树)中key对应的value值 private Value search(Node node, Key key) { if (node == null) { return null; } else if (node.getKey().compareTo(key) == 0) { return node.getValue(); } else if (node.getKey().compareTo(key) > 0) { return search(node.getLeft(), key); } else { return search(node.getRight(), key); } } //返回树中key对应的value值 public Value search(Key key) { return search(root, key); } //先序遍历 private void preOrder(Node node) { if (node == null) return; System.out.println(node.key); preOrder(node.getLeft()); preOrder(node.getRight()); } //先序遍历 public void preOrder() { preOrder(root); } //中序遍历 private void inOrder(Node node) { if (node == null) return; inOrder(node.getLeft()); System.out.println(node.getKey()); inOrder(node.getRight()); } //中序遍历 public void inOrder() { inOrder(root); } //后续遍历 private void postOrder(Node node) { if (node == null) return; postOrder(node.getLeft()); postOrder(node.getRight()); System.out.println(node.getKey()); } //后续遍历 public void postOrder() { postOrder(root); } //层序遍历 public void levelOrder() { if (root == null) return; java.util.LinkedList<Node> queue = new java.util.LinkedList<>(); queue.add(root); while (!queue.isEmpty()) { Node node = queue.pop(); System.out.println(node); if (node.getLeft() != null) { queue.add(node.getLeft()); } if (node.getRight() != null) { queue.add(node.getRight()); } } } //以node为根的树中,key最小的结点 private Node minNode(Node node) { if (node.getLeft() == null) return node; return minNode(node.getLeft()); } //树中key最小的结点 public Node minNode() { return minNode(root); } //以node为根的树中,key最大的结点 private Node maxNode(Node node) { if (node.getRight() == null) return node; return maxNode(node.getRight()); } //树中key最大的结点 public Node maxNode() { return maxNode(root); } //删除node为根的树(子树)中key最小的结点 private Node removeMin(Node node) { if (node == null) return null; if (node.getLeft() == null) { Node rightNode = node.getRight(); node.setRight(null); size--; return rightNode; } node.setLeft(removeMin(node.getLeft())); return node; } //删除树中key最小的结点 public void removeMin() { root = removeMin(root); } //删除node为根的树(子树)中key最大的结点 private Node removeMax(Node node) { if (node == null) return null; if (node.getRight() == null) { Node leftNode = node.getLeft(); node.setLeft(null); size--; return leftNode; } node.setRight(removeMax(node.getRight())); return node; } //删除树中key最大的结点 public void removeMax() { root = removeMax(root); } //删除一个结点 private Node remove(Node node, Key key) { if (node == null) return null; if (key.compareTo(node.key) < 0) {//如果比根小,去左子树删除,然后返回根 node.setLeft(remove(node.getLeft(), key)); return node; } else if (key.compareTo(node.key) > 0) {//如果比根大,去右子树删除,然后返回根 node.setRight(remove(node.getRight(), key)); return node; } else { //key == node.key //如果与当点子树的根key相等 if (node.getLeft() == null) { //判断当前子树的根是否有左子树 Node rightNode = node.getRight(); node.setRight(null); size--; return rightNode; } else if (node.getRight() == null) {//判断当前子树的根是否有右子树 Node leftNode = node.getLeft(); node.setLeft(null); size--; return leftNode; } else { // 如果当前子树既有左子树,又有右子树 Node successor = minNode(node.getRight());//寻找后继结点,也就是右子树中最小的结点 successor = new Node(successor.getKey(), successor.getValue());//新建一个与后继结点一模一样的,为了替换 size++;//相当于添加一个结点 successor.setRight(removeMin(node.getRight()));//删除后继结点,然后连上原来的右边 successor.setLeft(node.getLeft());//连上原来的左边 node.left = node.right = null;//原来的结点已经被替换了,可以不要了。 size--;//相当于删除一个节点 return successor;//当前新的子树根就是successor } } } public void remove(Key key) { root = remove(root, key); } public static void main(String[] args) { //建立一颗二叉搜索树 BinarySearchTree<String, String> bst = new BinarySearchTree<>(); //插入数据 bst.insert("dog", "狗,一种动物"); bst.insert("password", "密码"); bst.insert("cat", "猫,一种动物"); bst.insert("cup", "杯子"); bst.insert("tom", "汤姆,《猫和老鼠》中的猫"); bst.insert("jerry", "杰瑞,《猫和老鼠》中的老鼠"); bst.insert("a", "26个英文字母中的第一个"); //search() System.out.println(bst.search("a"));//26个英文字母中的第一个 System.out.println(bst.search("dog"));//狗,一种动物 System.out.println(bst.search("ttttt"));//null //contain() System.out.println(bst.contain("cup"));//true System.out.println(bst.contain("tom"));//true System.out.println(bst.contain("tttttt"));//false //maxNode() System.out.println(bst.maxNode());//Node{key=tom, value=汤姆,《猫和老鼠》中的猫} //minNode() System.out.println(bst.minNode());//Node{key=a, value=26个英文字母中的第一个} //removeMax() bst.removeMax(); System.out.println(bst.maxNode());//Node{key=password, value=密码} //removeMin() bst.removeMin(); System.out.println(bst.minNode());//Node{key=cat, value=猫,一种动物} //size() System.out.println(bst.size());//5 //levelOrder() bst.levelOrder(); //remove(); System.out.println("--------------"); bst.remove("password"); bst.preOrder(); } }
以上是关于二叉搜索树(Java实现)的主要内容,如果未能解决你的问题,请参考以下文章