当前位置: 首页 > news >正文

堆排序原理及代码

文章目录

  • 🍊自我介绍
  • 🍊堆排序
    • 一、什么是堆?
    • 二、堆的分类
  • 🍊堆排序的思路
    • 一、构建大顶堆
    • 二、排序过程
  • 🍊堆排序代码


你的点赞评论就是对博主最大的鼓励
当然喜欢的小伙伴可以:点赞+关注+评论+收藏(一键四连)哦~


🍊自我介绍

  Hello,大家好,我是小珑也要变强(也是小珑),我是易编程·终身成长社群的一名“创始团队·嘉宾”“内容共创官” ,现在我来为大家介绍一下有关物联网-嵌入式方面的内容。


🍊堆排序

一、什么是堆?

堆是一种类似完全二叉树的数据结构,可以分为大顶堆,小顶堆(也叫大根堆,小根堆),而堆排序就是基于这种结构而产生的一种程序算法。

二、堆的分类

分类
大顶堆:每个节点的值都大于或者等于其左右孩子的值。
小顶堆:每个节点的值都小于或者等于其左右孩子的值。

堆排序:若是需要进行堆排序的代码,一定需要先把树构建成大顶堆或者小顶堆,然后再进行排序。

🍊堆排序的思路

以下以数组 [4, 6, 8, 5, 9] 为例来梳理堆排序的思路。

一、构建大顶堆

  1. 首先明确完全二叉树的性质,对于数组中的元素,节点 i 的左子节点为 2 * i + 1 ,右子节点为 2 * i + 2 。
  2. 从最后一个非叶子节点开始调整,数组长度为 5,最后一个非叶子节点索引为 (5/2 - 1)=1 ,对应元素值为 6。
  • 以索引为 1 的节点(值为 6)为当前节点,左子节点索引为 3(值为 5),右子节点索引为 4(值为 9),比较三个值,9 最大,所以交换当前节点的值 6 和索引为 4 的节点的值 9。
  • 此时数组变为 [4, 9, 8, 5, 6] 。
  1. 接着处理索引为 0 的节点(值为 4)。
  • 左子节点索引为 1(值为 9),右子节点索引为 2(值为 8),比较三个值,9 最大,所以交换当前节点的值 4 和索引为 1 的节点的值 9。
  • 此时数组变为 [9, 4, 8, 5, 6] 。

经过上述步骤,大顶堆构建完成。

二、排序过程

  1. 此时堆顶元素 9 为最大值,将堆顶元素 9 与最后一个元素 6 交换。
  • 数组变为 [6, 4, 8, 5, 9] 。
  1. 由于交换后可能破坏了堆的性质,需要从堆顶开始调整堆,这里调整的堆大小为 4(因为已经确定了一个最大元素在最后位置)。
  • 以索引为 0 的节点(值为 6)为当前节点,左子节点索引为 1(值为 4),右子节点索引为 2(值为 8),比较三个值,8 最大,所以交换当前节点的值 6 和索引为 2 的节点的值 8。
  • 此时数组变为 [8, 4, 6, 5, 9] 。
  1. 重复上述过程,再次将堆顶元素 8 与当前未排序部分的最后一个元素 5 交换。
  • 数组变为 [5, 4, 6, 8, 9] 。
  • 调整堆,以索引为 0 的节点(值为 5)为当前节点,左子节点索引为 1(值为 4),无子节点,无需交换。
  1. 最后将堆顶元素 5 与当前未排序部分的最后一个元素 4 交换。
  • 数组变为 [4, 5, 6, 8, 9] 。

此时数组已经完全有序。堆排序完成。

🍊堆排序代码

#include <stdio.h>void swap_data(int *x,int *y)
{*x ^= *y;*y ^= *x;*x ^= *y;return ;
}//自调整构建大顶堆
void heap_adjust(int *arr,int start,int end)
{int father_node = start;int son_node = father_node * 2 + 1;while(son_node <= end){//比较两个子结点,找到较大的字节if(son_node + 1 <= end && arr[son_node] < arr[son_node + 1])	{son_node ++;	}//若是父节点 > 子节点 ,表示调整完毕if(arr[father_node] > arr[son_node]){return ;	}else{ //交换负责父子内容,在继续子节点与孙结点比较swap_data(&arr[father_node],&arr[son_node]);father_node = son_node;son_node = father_node * 2 + 1;}}return ;
}void heap_sort(int arr[],int len)
{int i = 0;//第一次建立大顶堆,找到从右到左,找到第一次非叶子结点//从后往前依次遍历for(i = len / 2 - 1;i >= 0;i--){heap_adjust(arr,i,len - 1);	}//每次将根结点和最后一个结点交换,然后在调整for(i = len - 1;i > 0;i--){swap_data(&arr[0],&arr[i]);	heap_adjust(arr,0,i - 1);}
}void print_array(int a[],int plen)
{int i = 0;for(i = 0;i < plen;i++){printf("%d ",a[i]);	}printf("\n");
}int main()
{int a[] = {15,7,3,20,17,8};	int len = sizeof(a)/sizeof(a[0]);print_array(a,len);heap_sort(a,len);print_array(a,len);return 0;
}

http://www.mrgr.cn/news/57347.html

相关文章:

  • C 语言入门教程
  • Linux基础 -- GCC 工具链的 `-fstack-usage` 用法
  • ElasticSearch-7.17.10集群升级至ElasticSearch-7.17.24
  • HCIP-HarmonyOS Application Developer 习题(十六)
  • 面经整理 八股 虾皮购物 Java后端开发 上
  • Python实现股票自动交易:步骤、要点与注意事项有哪些?
  • 关于使用 C# 处理水位数据多种格式的统一转换
  • input子系统的框架和重要数据结构详解
  • SpringBoot项目整合Mybatis-MySql数据库编程
  • 总集篇:环形链表(是否成环?环长度?入环点?)
  • 鸿蒙启航 | 搭建 HarmonyOS 开发环境来个 Hello World
  • Jenkins配置CI/CD开发环境(理论到实践的完整流程)
  • opencv 将相机图片转为视频 - python 实现
  • 计算机毕业设计Hadoop+大模型在线教育大数据分析可视化 学情分析 课程推荐系统 机器学习 深度学习 人工智能 大数据毕业设计
  • 信发软件之添加组件——未来之窗行业应用跨平台架构
  • 顺序表(一)(数据结构)
  • linux:线程id及线程互斥
  • python基础综合案例(数据可视化—折线图可视化)
  • 全栈面试题】模块5-1】Oracle/MySQL 数据库基础
  • Spring Cloud --- Sentinel 规则持久化
  • 前端-基础CSS总结常用
  • 七、数据库服务器(MySQL、PostgreSQL)的搭建
  • 基于Fourier的两个人形机器人:从改进的3D扩散策略之iDP3到从单个RGB视频中模仿学习的OKAMI
  • 【面试经典150】day 6
  • Flutter鸿蒙next 中如何实现 WebView【跳、显、适、反】等一些基础问题
  • 项目太多,拓展固态硬盘,要安装软件如何固定移动硬盘盘符? - 解决必剪本地作品丢失的问题