数据结构与算法之二叉树 ——in dart
用dart语言实现的二叉树,实现了插入、查找、删除,中序遍历、前序、后序遍历等功能。
1 class BinaryTree<E extends Comparable> { 2 Node<E> _root; 3 int _nodeNumbers; 4 5 BinaryTree() : _nodeNumbers = 0; 6 7 factory BinaryTree.from(Iterable<E> elements) { 8 var tree = BinaryTree<E>(); 9 for (var e in elements) tree.insert(e); 10 return tree; 11 } 12 13 bool get isEmpty => _root == null; 14 int get nodeNumbers => _nodeNumbers; 15 16 void clear() { 17 _root = null; 18 _nodeNumbers = 0; 19 } 20 21 bool delete(E value) { 22 var deleted = find(value); 23 if (deleted == null) return false; 24 _delete(deleted); 25 _nodeNumbers--; 26 return true; 27 } 28 29 Node<E> find(E value) { 30 var current = _root; 31 while (current != null) { 32 var c = value.compareTo(current.value); 33 if (c == 0) break; 34 current = c < 0 ? current.leftChild : current.rightChild; 35 } 36 return current; 37 } 38 39 void insert(E value) { 40 var inserted = Node(value); 41 if (isEmpty) { 42 _root = inserted; 43 } else { 44 var current = _root; 45 while (current != null) { 46 if (value.compareTo(current.value) <= 0) { 47 if (current.leftChild == null) { 48 current.leftChild = inserted; 49 inserted.parent = current; 50 break; 51 } else { 52 current = current.leftChild; 53 } 54 } else { 55 if (current.rightChild == null) { 56 current.rightChild = inserted; 57 inserted.parent = current; 58 break; 59 } else { 60 current = current.rightChild; 61 } 62 } 63 } 64 } 65 _nodeNumbers++; 66 } 67 68 void traverse(void func(E value), [TraverseOrder order]) { 69 _traverse(_root, order, func); 70 } 71 72 E get max { 73 if (isEmpty) throw TreeEmptyException(); 74 var maxNode = _root; 75 while (maxNode.rightChild != null) maxNode = maxNode.rightChild; 76 return maxNode.value; 77 } 78 79 E get min { 80 if (isEmpty) throw TreeEmptyException(); 81 return _minNode(_root).value; 82 } 83 84 Node<E> _minNode(Node<E> root) { 85 var minNode = root; 86 while (minNode.leftChild != null) minNode = minNode.leftChild; 87 return minNode; 88 } 89 90 void _delete(Node<E> deleted) { 91 var successor = _successor(deleted); 92 if (successor != null) _delete(successor); 93 if (deleted == _root) _root = successor; 94 _replace(deleted, successor); 95 } 96 97 static void _replace<E>(Node<E> deleted, Node<E> successor) { 98 if (deleted.parent != null) { 99 if (deleted.parent.leftChild == deleted) 100 deleted.parent.leftChild = successor; 101 else 102 deleted.parent.rightChild = successor; 103 } 104 105 if (successor != null) { 106 successor.parent = deleted.parent; 107 successor.leftChild = deleted.leftChild; 108 successor.rightChild = deleted.rightChild; 109 if (deleted.leftChild != null) deleted.leftChild.parent = successor; 110 if (deleted.rightChild != null) deleted.rightChild.parent = successor; 111 } 112 } 113 114 Node<E> _successor(Node<E> node) => 115 node.rightChild != null ? _minNode(node.rightChild) : node.leftChild; 116 117 static void _traverse<E>(Node<E> root, TraverseOrder order, void func(E e)) { 118 if (root == null) return; 119 switch (order) { 120 case TraverseOrder.preOrder: 121 func(root.value); 122 _traverse(root.leftChild, order, func); 123 _traverse(root.rightChild, order, func); 124 break; 125 case TraverseOrder.postOrder: 126 _traverse(root.leftChild, order, func); 127 _traverse(root.rightChild, order, func); 128 func(root.value); 129 break; 130 default: 131 _traverse(root.leftChild, order, func); 132 func(root.value); 133 _traverse(root.rightChild, order, func); 134 } 135 } 136 } 137 138 enum TraverseOrder { preOrder, inOrder, postOrder } 139 140 class Node<E> { 141 E value; 142 Node<E> parent, leftChild, rightChild; 143 144 Node(this.value); 145 } 146 147 148 class TreeEmptyException implements Exception { 149 const TreeEmptyException(); 150 String toString() => 'TreeEmptyException'; 151 }