首先先看看这个删除节点12后的树,还要保证该平衡二叉树的特性保持不变

删除节点详细分为三类:

第一类.所删除的节点是叶子节点,这样就可以先遍历这个树,然后找到需要删除的节点,把它free掉就好

第二类:就是所删除的节点只有一个左孩子,或者只有一个右孩子,则把该节点的孩子变为它父亲的孩子 ,然后删除这个结点

在这个例子把28删除,就是把30连接到12上

第三类:就是最麻烦的一类,假如我们要删除节点12,直接删除就会破坏了排序二叉树的结构,那么我们想到一个方法,就是把这类转换成第一类,那么重点来了,我们找到要删除的结点后,找到在这个节点左子树的最右的节点或者右子树的最左侧的节点,把这个节点的值覆盖到要删除的节点上,然后删除左子树的最右的节点或者右子树的最左侧的节点,

我们看这个例子:要删除12 先找到以12位根的左子树的最右的节点 就是数字6 ,把6覆盖到节点·12,然后删除节点6

或者找到右子树的最左边的节点 就是该树上的28,把28覆盖到节点12上,再删除28,就变成了第二类删除

代码如下:核心函数Search 和 DelNode

#include<stdio.h>
#include<stdlib.h>typedef struct node
{int nValue;struct node *pLeft;struct node *pRight;
}BinatyTree;void InsertNode(BinatyTree **pTree,int nNum)
{BinatyTree *pTemp = NULL;pTemp = (BinatyTree*)malloc(sizeof(BinatyTree));pTemp->nValue = nNum;pTemp->pLeft = NULL;pTemp->pRight = NULL;//空树if(*pTree == NULL){*pTree = pTemp;return;}//非空树BinatyTree *pNode = *pTree;while(1){if(nNum > pNode->nValue){//去右侧if(pNode->pRight == NULL){pNode->pRight = pTemp;return;}//向右走pNode = pNode->pRight;}else if(nNum < pNode->nValue){//去左侧if(pNode->pLeft == NULL){pNode->pLeft = pTemp;return;}pNode = pNode->pLeft;}else{printf("数据错误.\n");return;}}
}void CreateBST(int arr[],int nLength,BinatyTree **pTree)
{if(arr == NULL || nLength <=0)return;int i;for(i = 0;i<nLength;i++){InsertNode(pTree,arr[i]);}
}void Search(BinatyTree *pTree,int nNum,BinatyTree **pDel,BinatyTree **pFather)
{while(pTree != NULL){if(pTree->nValue == nNum){*pDel = pTree;return;}else if(pTree->nValue > nNum){*pFather = pTree;pTree = pTree->pLeft;}else {*pFather = pTree;pTree = pTree->pRight;}}
}void DelNode(BinatyTree **pTree,int nNum)
{if(*pTree == NULL)return;//查找BinatyTree *pDel = NULL;BinatyTree *pFather = NULL;Search(*pTree,nNum,&pDel,&pFather);if(pDel == NULL)return;//分析情况//两个BinatyTree *pMark = NULL;if(pDel->pLeft != NULL && pDel->pRight!= NULL){//找左的最右pMark = pDel;//向左走一步pFather = pDel;pDel = pDel->pLeft;while(pDel->pRight != NULL){pFather = pDel;pDel = pDel->pRight;}//值覆盖pMark->nValue = pDel->nValue;}//被删除节点是根节点if(pFather == NULL){*pTree = pDel->pLeft ? pDel->pLeft : pDel->pRight;free(pDel);pDel = NULL;return;}//被删除节点非根if(pDel == pFather->pLeft){pFather->pLeft = pDel->pLeft ? pDel->pLeft:pDel->pRight;free(pDel);pDel = NULL;return;}else{pFather->pRight = pDel->pLeft ? pDel->pLeft:pDel->pRight;free(pDel);pDel = NULL;return;}
}void Traversal(BinatyTree *pTree)
{if(pTree == NULL)return;Traversal(pTree->pLeft);printf("%d ",pTree->nValue);Traversal(pTree->pRight);
}int main()
{int arr[] = {10,38,2,100,80,15,1,8,16};BinatyTree *pTree = NULL;CreateBST(arr,sizeof(arr)/sizeof(arr[0]),&pTree);Traversal(pTree);printf("\n");DelNode(&pTree,10);Traversal(pTree);return 0;
}

排序二叉树节点的删除相关推荐

  1. 一步一步写算法(之排序二叉树删除-1)

    [ 声明:版权所有,欢迎转载,请勿用于商业用途.  联系信箱:feixiaoxing @163.com] 相比较节点的添加,平衡二叉树的删除要复杂一些.因为在删除的过程中,你要考虑到不同的情况,针对每 ...

  2. 研磨数据结构与算法-13删除二叉树节点

    节点: /* * 二叉树节点 */ public class Node { //数据项 public long data; //数据项 public String sData; //左子节点 publ ...

  3. 数据结构 day07 基础知识学习 (二叉树 的 前中后遍历 ,插入节点,删除叶子节点, 二叉树的节点个数 )

    一.今天有点迷. 二.希望大家看的懂代码 ,我已经很努力写注释了. 三.这次的知识很基础 ,(老师关于 二叉树节点删除的哪里 讲的有点差 ,主要是讲之前没有打好框架   (关于父节点的定义   )  ...

  4. 牛牛有一棵n个节点的二叉树,该二叉树每个节点的权值为1。牛牛想要删掉该树其中的k层节点,删除序列为a1,a2...ak。 如有一棵二叉树,删除其中的第3层节点

    题目:牛牛有一棵n个节点的二叉树,该二叉树每个节点的权值为1.牛牛想要删掉该树其中的k层节点,删除序列为a1,a2-ak. 如有一棵二叉树,删除其中的第3层节点 思路: 层序遍历,遍历时对节点依次进行 ...

  5. 一步一步写算法(之排序二叉树删除-3)

    [ 声明:版权所有,欢迎转载,请勿用于商业用途.  联系信箱:feixiaoxing @163.com] 3 普通节点的删除 3.1 删除的节点没有左子树,也没有右子树 测试用例1: 删除节点6 /* ...

  6. 一步一步写算法(之排序二叉树删除-2)

    [ 声明:版权所有,欢迎转载,请勿用于商业用途.  联系信箱:feixiaoxing @163.com] 2.4 删除节点的左右子树都存在,此时又会分成两种情形 1)左节点是当前左子树的最大节点,此时 ...

  7. java实现排序二叉树

    * 二叉树排序算法看似很简单,特别是看到其他博客写的实现代码,但是如果把细节各种情况考虑进去,还是不容易的. * 数据使用链式二叉树来存储,在增加节点的时候,小的在父节点的左边,大的在父节点的右边.刚 ...

  8. 数据结构之二叉搜索树/二叉查找数/有序二叉树/排序二叉树

    概念~ 二叉查找树(英语:Binary Search Tree),也称二叉搜索树.有序二叉树(英语:ordered binary tree),排序二叉树(英语:sorted binary tree), ...

  9. 一步一图一代码之排序二叉树

    作者:禅楼望月(http://www.cnblogs.com/yaoyinglong/) 属性: ①若它的左子树不为空,则左子树上所有节点的值均小于它的根节点的值. ②若它的右子树不为空,则右子树上所 ...

最新文章

  1. 计算机进桌面后反复重启,我的电脑一插网线就自动重启。到界面之后又马上重启。一直循环。...
  2. OOP 中的 方法调用、接口、鸭式辩型、访问者模式
  3. python 格式化工具_Google的Python代码格式化工具YAPF详解
  4. linux access源码,从零开始学习Linux:Day04 源码安装Nginx 。acess/status/referer
  5. (01)VTK读取OBJ格式模型
  6. 电动牙刷C语言程序,电动牙刷的日常维护
  7. 一种人脸识别活体检测方法
  8. html鼠标移上去变成箭头,js实现鼠标移动到div上变成箭头
  9. 【游戏】——微信打飞机
  10. canvas 实现图片局部模糊_HTML5 Canvas图片马赛克模糊动画
  11. 【RabbitMQ】java.lang.NoClassDefFoundError: org/springframework/util/backoff/BackOff
  12. 国产银河数字式电子计算机是属于什么,邱桂香老师-计算机基础.ppt
  13. 小猫爪:i.MX RT1050学习笔记2-下载
  14. 鱼眼参数的数值计算优化方法
  15. 汽车ISP的“去留”之谜
  16. [家里蹲大学数学杂志]第266期中南大学2013年高等代数考研试题参考解答
  17. java生成PDF 导出
  18. SuperMap GIS点云数据处理QA
  19. 适合程序员表白的情话【保你脱单】
  20. 【iOS沉思录】Objective-C语言消息传递机制三道防线:消息转发机制详解

热门文章

  1. 计算机中单元格地址如何命名,单元格命名_怎样给单元格重新命名或是删除单元格名称_vba...
  2. C语言 如何给结构体中的数组赋值
  3. WIN10系统让服务程序自启动
  4. nagios安装与配置教程(详细版)【入门教程】2020-11-16
  5. java中有关hashset_java中HashSet详解
  6. 叮,你收到一份来自CNCF的云原生景观简介
  7. java面试突击_两个月!终于把《JavaGuide面试突击》v3.0肝出来了!
  8. 机器学习-Boosting(AdaBoost、GBDT)
  9. 回应张逸老师(二)小甜甜和牛夫人?
  10. 前端项目实战30-多加一个列表表示详情