平衡二叉树详解

news2025/1/11 22:46:21

目录

平衡二叉树的定义

平衡二叉树的基本操作

查找

插入

AVL树的建立

平衡二叉树的定义

平衡二叉树仍然是一棵二叉查找树,只是在其基础上增加了平衡的要求,也就是其左右子树的高度之差的绝对值不超过1。

在定义树的结构时需要加入一个变量height,用来记录以当前结点为根节点的子树的高度。

struct node{
	int v,height;
	node *lchild,*rchild;
};

在这种定义下,如果需要新建一个结点,就可以使用如下写法:

node* newNode(int v){
	node* Node=new node;
	Node->v=v;
	Node->height=1;
	Node->lchild=Node->rchild=NULL;
	return Node;
}

显然,可以通过下面的函数获取结点root所在子树的当前高度:

int getheight(node* root){
	if(root==NULL){
		return 0;
	}
	return root->height;
}

于是根据定义,就可以通过下面的函数计算左右子树的高度差:

int getbalancefactor(node* root){
	return getheight(root->lchild)-getheight(root->rchild);
}

显然,结点root所在子树的高度等于其左右子树高度的较大值加1.

void updateheight(node* root){
	root->height=max(getheight(root->lchild),getrchild(root->rchild))+1;
}

平衡二叉树的基本操作

查找

void search(node* root,int x){
	if(root==NULL){
		printf("search failed\n");
		return;
	}
	if(x==root->data){
		printf("%d\n",root->data);
	}
	else if(x<root->data){
		search(root->lchild,x);
	}
	else{
		search(root->rchild,x);
	}
}

插入

左旋的代码

void L(node* &root){
	node* temp=root->rchild;
	root->rchild=temp->lchild;
	temp->lchild=root;
	updataheight(root);
	updataheight(temp);
	root=temp;
}

右旋的代码

void R(node* &root){
	node* temp=root->lchild;
	root->lchild=temp->rchild
	temp->rchild=root;
	updataheight(root);
	updataheight(temp);
	root=temp;
}

对于各种树型使用的操作如下:

 首先,AVL树的插入代码是在二叉查找树的插入代码的基础上增加平衡操作的,因此,如果不考虑平衡操作,代码是下面这样的:

void insert(node* &root,int v){
	if(root==NULL){
		root=newNode(v);
		return;
	}
	if(v<root->data){
		insert(root->lchild,v);
	}
	else{
		insert(root->rchild,v);
	}
}

在这个基础上,由于需要从插入的结点开始从下往下判断结点是否失衡,因此需要在每个insert函数之后更新当前子树的高度,并在这之后根据树型是LL型、LR型、RR型、RL型之一来进行平衡操作。

void insert(node* &root,int v){
	if(root==NULL){
		root=newNode(v);
		return;
	}
	if(v<root->data){
		insert(root->lchild,v);
		updataheight(root);
		if(getbalancefactor(root)==2){
			if(getbalancefactor(root->lchild)==1){//L型 
				R(root);
			}
			else if(getbalancefactor(root->lchild)==-1){//LR型 
				L(root->lchild);
				R(root);
			}
		}
	}
	else{
		insert(root->rchild,v);
		updataheight(root);
		if(getbalancefactor(root)==-2){
			if(getbalancefactor(root->lchild)==-1){//RR型 
				L(root);
			}
			else if(getbalancefactor(root->rchild)==1){//RL型 
				R(root->rchild);
				L(root);
			}
		}
	}
}

AVL树的建立

node* Create(int data[],int n){
	node* root=NULL;
	for(int i=0;i<n;i++){
		insert(root,data[i]);
	}
	return root;
} 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1803385.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

使用树莓派和 L298N 来 DIY 小车底盘

树莓派小车可以作为 STEM&#xff08;科学、技术、工程、数学&#xff09;教育的工具&#xff0c;在实际操作中帮助学生理解和学习电子技术、编程和机器人原理。可以培养学生的动手能力、解决问题的能力和创新思维。 随着近年 AI 技术的高速发展&#xff0c;SLAM、VSLAM 甚至带…

SpringBoot+Vue图书管理系统(前后端分离)

技术栈 JavaSpringBootMavenMySQLMyBatisVueShiroElement-UI 角色对应功能 用户管理员 功能截图

STM32关于uc/OS-III的多任务程序

目录 一、UCOS-III源码获取 二、HAL库工程的建立 1.RCC配置 2.SYS配置 3.USART1配置 4.GPIO配置 5.时钟配置 6.项目配置 三、KEil文件添加 1.文件复制 2.KEil工程添加 3.添加文件路径 四、代码修改 1. 2.修改文件app_cfg.h中代码 3.修改include.h的代码 4.修改…

常见的api: BigInteger

一.获取一个大的随机整数 1.代码: BigInteger bd1 new BigInteger(4, new Random());System.out.println(bd1); 2.打印的结果:2 3.注释获取的是0-16之间的随机整数 二.获取一个指定的大的数 1.代码&#xff1a; BigInteger bd2 new BigInteger("100");System.o…

计网总结☞物理层

五层协议体系结构->各层的功能有&#xff1a; 物理层 物理层的任务就是尽可能地屏蔽传输媒体的差异&#xff0c;透明地传送比特流&#xff08;注意&#xff1a;传递信息的物理媒体&#xff0c;如双绞线、同轴电缆、光缆等&#xff0c;是在物理层的下面&#xff0c;当做第 0…

flink读取hive写入http接口

目录 0、创建hive数据 1、pom.xml 2、flink代码 3、sink 4、提交任务jar 5、flink-conf.yaml 6、数据接收 flink-1.17.2jdk1.8hive-3.1.3hadoop3.3.6passwordhttp0、创建hive数据 /cluster/hive/bin/beeline !connect jdbc:hive2://ip:10000 create database demo; d…

HPC: perf入门

如果你想查看你的程序在cpu上运行时&#xff0c;耗时时如何分布的&#xff0c;那么perf是一个合理的选择。 准备工作 为了支持使用perf&#xff0c;首先你要安装相关的库 sudo apt install linux-tools-5.15.0-67-generic此外&#xff0c;因为使用perf进行benchmark&#xf…

【C语言】预处理详解(上卷)

前言 预处理也是C语言中非常重要的存在。那么就详细地来了解一下吧。 预定义符号 C语言设置了一些预定义符号&#xff0c;可以直接使用&#xff0c;预定义符号也是在预处理期间处理的。 1 __FILE__ //进行编译的源文件 2 __LINE__ //文件当前的…

移动端 UI 风格,视觉盛宴

移动端 UI 风格&#xff0c;视觉盛宴

【Proteus8.16】Proteus8.16.SP3.exe的安装包,安装方法

下载&#xff1a; 链接&#xff1a;https://pan.baidu.com/s/14ZlETF7g4Owh8djLaHwBOw?pwd2bo3 提取码&#xff1a;2bo3 管理员打开proteus8.16.SP3.exe一路装就行了&#xff0c;许可证选Licence2.lxk,点安装后关闭&#xff0c;然后继续装完。 然后打开Patch-Proteus-8.16-…

tomcat8w.exe指向了别的tomcat

这种情况通常发生是因为Tomcat服务在注册表中的配置指向了错误的可执行文件路径。tomcat8w.exe是一个Windows服务配置工具&#xff0c;它用于管理Tomcat服务&#xff0c;包括设置Path to executable&#xff0c;即指向Tomcat服务实际启动的.exe文件的路径。如果Path to executa…

基于深度学习的在线选修课程推荐系统

基于深度学习的在线选修课程推荐系统 1、效果图 点我查看Demo 2、功能 可联系我-微-信(1257309054) 登录注册、点赞收藏、评分评论&#xff0c;课程推荐&#xff0c;热门课程&#xff0c;个人中心&#xff0c;可视化&#xff0c;后台管理&#xff0c;课程选修3、核心推荐代…

htb_office

端口扫描 namp -sSVC 10.10.11.1380&#xff0c;445 80端口 robots.txt 只有/administrator可以访问 Joomla joomscan扫描 joomscan --url http://10.10.11.3/ 版本为4.2.7&#xff0c;存在cve CVE-2023-23752 Joomla未授权访问Rest API漏洞 访问路径 /api/index.php/…

linux经典例题编程

编写Shell脚本&#xff0c;计算1~100的和 首先vi 1.sh,创建一个名为1.sh的脚本&#xff0c;然后赋予这个脚本权限&#xff0c;使用命令chmod 755 1.sh&#xff0c;然后就可以在脚本中写程序&#xff0c;然后运行。 shell脚本内容 运行结果&#xff1a; 编写Shell脚本&#xf…

【JavaScript】内置对象 - 字符串对象 ⑤ ( 判断对象中是否有某个属性 | 统计字符串中每个字符出现的次数 )

文章目录 一、判断对象中是否有某个属性1、获取对象属性2、判定对象是否有某个属性 二、统计字符串中每个字符出现的次数1、算法分析2、代码示例 String 字符串对象参考文档 : https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/String 一、判…

OpenCV学习(4.8) 图像金字塔

1.目的 在这一章当中&#xff0c; 我们将了解图像金字塔。我们将使用图像金字塔创建一个新的水果&#xff0c;“Orapple”我们将看到这些功能&#xff1a; cv.pyrUp&#xff08;&#xff09; &#xff0c; cv.pyrDown&#xff08;&#xff09; 在通常情况下我们使用大小恒定…

Rust 标记一个属性或函数为废弃

如题&#xff0c;演示Rust 标记一个属性或函数为废弃的基本使用方法&#xff1a; 示例&#xff1a; use serde::{Deserialize, Serialize};#[derive(Clone, Debug, Serialize, Deserialize, Default)] pub struct GrpcOptions {pub addr: String,pub max_recv_message_size: u…

MathType7.8学术必备神器 科研利器 教学好帮手

【MathType 7.8】数学公式编辑器&#xff0c;让学术和专业文档制作更高效、更准确&#xff01;&#x1f9ee;✨ 作为一名软件技术专家&#xff0c;我一直在寻找一款能够轻松创建复杂数学公式的工具。幸运的是&#xff0c;我终于找到了MathType 7.8&#xff0c;这款强大的数学公…

数学+思维,CF1056B - Divide Candies

一、题目 1、题目描述 2、输入输出 2.1输入 2.2输出 3、原题链接 Problem - 1056B - Codeforces 二、解题报告 1、思路分析 考虑i^2 j^2 | m 而m的余数有限&#xff0c;且m很小 我们枚举两重循环&#xff0c;都枚举m的余数&#xff0c;分别记为x&#xff0c;y 如果x ^ …

vue2组件封装实战系列之tag组件

作为本系列的第一篇文章&#xff0c;不会过于的繁杂&#xff0c;并且前期的组件都会是比较简单的基础组件&#xff01;但是不要忽视这些基础组件&#xff0c;因为纵观elementui、elementplus还是其他的流行组件库&#xff0c;组件库的封装都是套娃式的&#xff0c;很多复杂组件…