
二叉树基本使用
层级限制:第i层最多包含2^(i-1)个节点。 深度限制:深度为k的二叉树最多有2^k -1个节点。 高度规律:n节点的二叉树高度至少为log2(n+1)(通常实用性较低)。 满二叉树:每层完全满足节点数量,即高度为h时拥有2^h -1个节点。 完全二叉树:所有叶子节点仅出现在最底层,且最低层全部集中在左侧。 双满二叉树:同时满足满二叉树和完全二叉树条件,优化率最高。 无左无右:直接删除,调整父子引用。 只有左或右:替换空缺位置。 两子都有:找到继承者,替换原节点。 前序遍历:根→左→右 中序遍历:左→根→右 后序遍历:左→右→根
发布日期:2021-05-26 07:28:42
浏览次数:20
分类:精选文章
本文共 7468 字,大约阅读时间需要 24 分钟。
二叉树概述与常用操作
二叉树是一种常见的数据结构,广泛应用于查找和排序操作中。它以数组或链表的速度优势,成为高效数据处理的重要工具。本文将深入探讨二叉树的基本概念、类型及其应用方法。
二叉树的定义
二叉树是指每个结点最多有两个子节点的树形结构。通常称左子树(left subtree)和右子树(right subtree)。二叉树在键值存储和检索方面具有独特优势,与数组的查找速度和链表的插入删除速度结合,一旦实现后,操作效率显著提升。
二叉树的关键特质
二叉树的分类
二叉搜索树属性
二叉查找树(BST)基于特定规定:任意节点所有左子树节点值小于父值,右子树节点值大于父值。保障较高的查询效率。
二叉树操作方法
1. 查找操作
查找过程从根节点开始:若目标值小于当前节点,转向左子树;若大于,转向右子树。若当前节点为None,返回null。
示例:查找节点13,路径为:
- 根节点15 → 左子节点5 → 右子节点12 → 左子节点13。
2. 插入操作
插入坐标类似查找,但非存在时新增节点。插入13:
- 根节点15 → 左子10 → 右子14 → 根节点即插入。
3. 删除操作
删除分为几种情况:
例如,删除节点25的过程涉及检查左右结构,找其继继承者,并更新父节点引lw。
二叉树遍历方法
这些遍历方式不同访问顺序,常用于数据处理任务选择优化。
实现代码示例
以下代码展示了Node结构、查找、插入、删除和遍历方法。
class Node { public int iData; // 数据键值 public double dData; // 数据值 public Node leftChild; public Node rightChild; public void displayNode() { System.out.println("{ " + iData + ", " + dData + " }"); }}class Tree { Node root; public Tree() { root = null; } public Node find(int key) { Node current = root; while (current != null) { if (key < current.iData) { current = current.leftChild; } else { current = current.rightChild; } } return current; } public void insert(int id, double dd) { Node newNode = new Node(); newNode.iData = id; newNode.dData = dd; if (root == null) { root = newNode; } else { Node current = root; Node parent = current; while (true) { parent = current; if (id < current.iData) { current = current.leftChild; if (current == null) { parent.leftChild = newNode; break; } } else { current = current.rightChild; if (current == null) { parent.rightChild = newNode; break; } } } } } public boolean delete(int key) { Node current = root; Node parent = root; boolean isLeftChild = true; while (current.iData != key) { parent = current; if (key < current.iData) { isLeftChild = true; current = current.leftChild; } else { isLeftChild = false; current = current.rightChild; } if (current == null) { return false; } } Node successor; if (current.leftChild == null && current.rightChild == null) { if (current == root) { root = null; } else if (isLeftChild) { parent.leftChild = null; } else { parent.rightChild = null; } } else if (current.leftChild == null) { if (current == root) { root = current.rightChild; } else if (isLeftChild) { parent.leftChild = current.rightChild; } else { parent.rightChild = current.rightChild; } } else if (current.rightChild == null) { if (current == root) { root = current.leftChild; } else if (isLeftChild) { parent.leftChild = current.leftChild; } else { parent.rightChild = current.leftChild; } } else { successor = getSuccessor(current); if (current == root) { root = successor; } else if (isLeftChild) { parent.leftChild = successor; } else { parent.rightChild = successor; } successor.leftChild = null; successor.rightChild = null; } return true; } private Node getSuccessor(Node delNode) { Node successorParent = delNode; Node successor = delNode.rightChild; Node current = delNode.rightChild; while (current != null) { successorParent = successor; successor = current; current = current.leftChild; } if (successor != delNode.rightChild) { successorParent.leftChild = successor.rightChild; successor.rightChild = delNode.rightChild; } return successor; } public void displayTree() { Stack globalStack = new Stack(); globalStack.push(root); int nBlanks = 32; boolean isRowEmpty = false; System.out.println("========================================================================"); while (!isRowEmpty) { Stack localStack = new Stack(); isRowEmpty = true; for (int j = 0; j < (root.depth +1); j++) { localStack.push(globalStack.pop()); } while (!localStack.isEmpty()) { Node current = localStack.pop(); localStack.push(current.rightChild); localStack.push(current); System.out.print(" "); } System.out.println("========================================================================"); } } List preList = new ArrayList(); List afterList = new ArrayList(); List inList = new ArrayList(); void preOrder(Node localRoot) { if (localRoot != null) { preList.add(localRoot.iData); preOrder(localRoot.leftChild); preOrder(localRoot.rightChild); } } void inOrder(Node localRoot) { if (localRoot != null) { inOrder(localRoot.leftChild); inList.add(localRoot.iData); inOrder(localRoot.rightChild); } } void postOrder(Node localRoot) { if (localRoot != null) { postOrder(localRoot.leftChild); postOrder(localRoot.rightChild); afterList.add(localRoot.iData); } } void traverse(int type) { switch (type) { case 1: System.out.print("\npre order : "); preOrder(root); break; case 2: System.out.print("\nin order : "); inOrder(root); break; case 3: System.out.print("\npost order : "); postOrder(root); break; default: break; } } public static void main(String[] args) { Tree theTree = new Tree(); theTree.insert(50, 1.3); theTree.insert(25, 1.1); theTree.insert(75, 1.7); theTree.insert(12, 1.3); theTree.insert(37, 1.9); theTree.insert(43, 1.4); theTree.insert(87, 1.6); theTree.insert(93, 1.2); theTree.insert(97, 1.5); theTree.insert(30, 1.4); theTree.insert(19, 1.3); Node node = theTree.find(93); System.out.println(node.dData); theTree.displayTree(); System.out.println("\n删除一个节点 -------------"); theTree.delete(25); theTree.traverse(1); }}
测试与验证
通过上述代码和树形结构,可以运行测试程序观察结果。查找、插入、删除操作均可验证。最终,可以自行修改数据填充以适应具体需求。
二叉树作为基础数据结构,在数据存储管理中的应用广泛。理解其原理和运用方法,对于数据结构与算法的学习至关重要,同时也是提升编程能力的关键环节。
发表评论
最新留言
路过,博主的博客真漂亮。。
[***.116.15.85]2025年04月29日 04时33分52秒
关于作者

喝酒易醉,品茶养心,人生如梦,品茶悟道,何以解忧?唯有杜康!
-- 愿君每日到此一游!
推荐文章
112. 路径总和(Javascript)
2019-03-21
G1 如何做到可预测的停顿和G1 垃圾收集器入门
2019-03-21
0X3协议与数据包
2019-03-21
C++ 函数需要有返回值,但非全分支return(RVO)
2019-03-21
python解释器环境问题
2019-03-21
图像质量评估仿真
2019-03-22
uni-app快速导入自己需要的插件
2019-03-22
作为公共组软件工程师如何工作
2019-03-22
uni-app 微信支付
2019-03-22
编写xor_shellcode.py
2019-03-22
Echarts笔记
2019-03-22
Ubuntu 20.04 Docker 安装并配置
2019-03-22
[小技巧]新建txt菜单
2019-03-22
【问答23】Linux移植:如何制作rootfs?
2019-03-22
Java虚拟机详解(五)------JVM参数(持续更新)
2019-03-22
在 eclipse 中将 web 项目部署到 tomcat 服务器上
2019-03-22
ffmpeg结构体(3)-之AVPacket及其相关函数
2019-03-22
iOS关于申请公司开发者账号缴费支付
2019-03-22
寻找两个有序数组的中位数
2019-03-22
10-3 A1-4在产品表中找出库存数量大于50的产品的信息 (20 分)
2019-03-22