堆数据结构+堆排序+最大优先队列的堆的实现

堆(Heap)的原理与C++实现 堆(Heap)是一种特殊的树形数据结构,通常用于实现优先队列。最大堆(Max Heap):每个节点的值都大于或等于其子节点的值。最小堆(Min Heap):每个节点的值都小于或等于其子节点的值。堆通常是一个完全二叉树,这意味着除了最后一层,其他层都是完全填满的,并且最后一层的节点都尽可能地靠左排列。堆是一种非常高效的数据结构,特别适用于需要频繁获取最大或最小元素的场景。通过数组实现堆,可以充分利用其完全二叉树的性质,使得插入、删除和构建堆的操作都能在 O(log n) 的时间内完成。 阅读详情

对于堆排序,首先要先知道什么是堆数据结构,堆数据结构就是一个完全二叉树,但是它有自己的性质.
例如最大堆的性质为:A[PARENT[i]]>=A[i];即每一个结点的值大于等于其左右孩子的值,小于等于其父节点的值。我们在这里只讨论最大堆的情况。我们知道一颗完全二叉树对应一个最大堆的形式,我们要做的就是将二叉树转化为最大堆,这就是所谓的最大堆的维护,我们定义函数MaxheapFY(A,i)来进行操作。
代码:

/**
 *MaxheapFY(A,i):维护位置i最大堆性质,此时假设left(i)和right(i)为根的两颗二叉树都是最大堆,
 */
void MaxheapFY(int *A,int i){//维护位置i最大堆性质,
    int l,r,now;
    l=LEFT(i);
    r=RIGHT(i);
    now=i;//记录当前结点
    if(l<=heapsize&&A[l]>A[now]){
        now=l;//交换A[l]和A[i],并递归维护下一个当前结点now
    }
    if(r<=heapsize&&A[r]>A[now]){
        now=r;//交换A[l]和A[i],并递归维护下一个当前结点now
    }
    if(now!=i){//不是当前结点,需要进行交换,用当前结点与左右孩子的最大值进行交换
        swap(A[i],A[now]);
        MaxheapFY(A,now);//递归维护当前结点,直到叶子结点
    }
}

下面就是依据最大堆的维护性质进行建堆:
/**
*BuildMaxHeap(A,n):输入一个无序数组 A[1…n],建立最大堆,我们知道数组A[(n/2+1)…n]中的元素都是
*树中的叶子结点,每一个都可以看做是一个元素的最大堆,那么我们还记得MaxheapFY(A,i)函数用来维护
*最大堆的前提是其孩子Left(i),Right(i)都是最大堆,因此我们可以利用MaxheapFY(A,i)函数,从i:[(n/2)..1]
*实现最大堆的建立。
*/
代码:

void BuildMaxHeap(int *A,int n){//A[1..n]
    heapsize=n;//全局变量,表示最大堆的大小
    for(int i=n/2;i>=1;i--){//从n/2..1维护堆中每个节点的最大堆性质:结点的值大于起孩子的值
        MaxheapFY(A,i);
    }
}

我们知道最大堆的第一个元素肯定是数组中最大值,我们可以交换(A[1]和A[n])此时A[n]中已经是最大的值了,不需要在操作,只需要维护剩下的n-1个元素的下标为1的最大堆性质,运行之后就变成n-1个元素的最大堆,继续进行上面的交换操作直到剩下2个元素,就已经完成排序。
代码:

void HeapSort(int *A,int n){
    BuildMaxHeap(A,n);//建立最大堆
    for(int i=n;i>=2;i--){
        //cout<<A[1]<<" ";
        swap(A[1],A[i]);//交互A[1]和A[i],使得A[i]中为当前最大的元素
        heapsize--;//堆大小减去1,便于下次操作去掉已经排好序的元素
        MaxheapFY(A,1);//此时A[1]不一定满足最大堆的性质,重新维护下标1的最大堆的性质
    }
}

至此我们已经完成了最大堆的建立和堆排序的代码,最大堆还有一个更重要的用处,就是基于最大堆的最大优先队列的实现,最大优先队列就是最大元素优先,当然也有最小优先队列,是基于最小堆进行构造的。我们学过数据结构都知道,每一个数据结构都有其所为的属性和操作(方法或者是函数),我们就来看一下最大优先级队列应该支持什么样的操作呢。肯定会有:取队列的首元素,删除首元素,插入元素,修改元素关键字的值等的操作。
/**
*下面给出最大优先级队列对应的操作
*1、PQueue_Insert(A,x):把元素x插入到集合S中,集合S对应的是一种最大优先级队列
*2、PQueue_Maxnum(A):返回最大优先级队列S中,键值最大的元素
*3、PQueue_Pop(A):去掉并返回最大优先级队列S最大键值的元素并删除
*4、PQueue_IncresaseKey(A,x,key):将元素x的关键字的值增加到key(尽对应这里的最大优先级队列)
*
*特别注意:::
*这里的优先级队列是基于最大堆建立的后,进行维护和操作的,因此在进行最大优先级队列
*操作之前,必须先进行初始胡函数PQueue_Init(A,n):初始化长度为n集合S,构造成最大堆
*/
各种函数代码实现:
初始化函数PQueue_Init(A,n):

void PQueue_Init(int *A,int n){
    BuildMaxHeap(A,n);//调用建立最大堆的函数进行初始化
}

返回最大元素的函数PQueue_Maxnum(A):

int PQueue_Maxnum(int *A){
    return A[1];
}

去掉并返回最大优先级队列的首元素PQueue_Pop(A):

int PQueue_Pop(int *A){
    if(heapsize>=1){
        int max=A[1];
        A[1]=A[heapsize];
        --heapsize;//堆大小(最大优先级队列的大小)减去1,
        MaxheapFY(A,1);//维护剩下的heaps的最大堆的性质
        return max;
    }
    else return -1;//删除失败
}

修改元素关键字后并维护的函数PQueue_IncresaseKey(A,x,key):

int PQueue_IncresaseKey(int *A,int i,int key){//增大A[i]的键值
    if(key<A[i]) return -1;//不符合最大堆的要求(仅仅是这里的定义)

    A[i]=key;//注意此时i的所有祖先都有可能不在满足最大堆的性质,
             //因此我们余姚判断所有的祖先是否满足最大堆的要求
    while(i>1&&A[PARENT(i)]<A[i]){
        swap(A[i],A[PARENT(i)]);
        i=PARENT(i);//向上判断到达当前的当前的结点满足最大堆的性质或者到达祖宗结点
    }
}

插入元素PQueue_Insert(A,x):

void PQueu_Insert(int *A,int key){
    //插入首先最大优先级队列的大小增加1
    ++heapsize;
    A[heapsize]=INF;//对新增的结点赋值一个永远娶不到的最小的值(仅对应于本程序的最大优先级队列)
    //剩下的操作就相当于将下标heapsize的关键字增大到key后,进行维护了,直接调用函数就好了
    PQueue_IncresaseKey(A,heapsize,key);

}

至此所有函数定义并实现完成,这就是最大优先队列。

附录全部代码及测试(少数):

/**
  *@xiaoran
  *堆排序,是一种借助数据结构堆进行原地排序的算法,
  *首先了解什么堆数据结构,如何构造最大堆以及维护最大堆
  *以及用对数据结构构造高效的优先级队列
  */
#include<iostream>
#include<cstdio>
#include<map>
#include<cstring>
#include<string>
#include<algorithm>
#include<queue>
#include<vector>
#include<stack>
#include<cstdlib>
#include<cctype>
#include<cmath>
#define LL long long

#define PARENT(x) x>>1
#define LEFT(x) x<<1
#define RIGHT(x) (x<<1)+1

#define INF -100000000
#define PT(A,n) for(int i=1;i<=n;i++) cout<<A[i]<<" "; cout<<endl;


using namespace std;

int heapsize=0;//堆的大小

/**
 *输出A[1..n]
 */
void Print(int *A,int n){
    for(int i=1;i<=n;i++) cout<<A[i]<<" ";
    cout<<endl;
}

/**
 *MaxheapFY(A,i):维护位置i最大堆性质,此时假设left(i)和right(i)为根的两颗二叉树都是最大堆,
 */
void MaxheapFY(int *A,int i){//维护位置i最大堆性质,
    int l,r,now;
    l=LEFT(i);
    r=RIGHT(i);
    now=i;//记录当前结点
    if(l<=heapsize&&A[l]>A[now]){
        now=l;//交换A[l]和A[i],并递归维护下一个当前结点now
    }
    if(r<=heapsize&&A[r]>A[now]){
        now=r;//交换A[l]和A[i],并递归维护下一个当前结点now
    }
    if(now!=i){//不是当前结点,需要进行交换,用当前结点与左右孩子的最大值进行交换
        swap(A[i],A[now]);
        MaxheapFY(A,now);//递归维护当前结点,直到叶子结点
    }
}
/**
 *BuildMaxHeap(A,n):输入一个无序数组A[1...n],建立最大堆,我们知道数组A[(n/2+1)...n]中的元素都是
 *树中的叶子结点,每一个都可以看做之和一个元素的最大堆,那么我们还记得MaxheapFY(A,i)函数用来维护
 *最大堆的前提是其孩子Left(i),Right(i)都是最大堆,因此我们可以利用MaxheapFY(A,i)函数,从i:[(n/2)..1]
 *实现最大堆的建立。
 */
void BuildMaxHeap(int *A,int n){//A[1..n]
    heapsize=n;
    for(int i=n/2;i>=1;i--){//从n/2..1维护堆中每个节点的最大堆性质:结点的值大于起孩子的值
        MaxheapFY(A,i);
    }
}
/**
 *下面利用上面两个函数进行构造堆排序算法HeapSort(A,n);
 *调用BuildMaxHeap(A,n)将输入数组A[1..n]建立为最大堆。注意此时数组的最大值为A[1],
 *我们只要交换A[1]和A[n],去掉A[n](--heapsize),维护线标1的最大堆的性质即可:MaxheapFY(A,1),
 *直到堆的大小n-1降到2
 */
void HeapSort(int *A,int n){
    BuildMaxHeap(A,n);//建立最大堆
    for(int i=n;i>=2;i--){
        //cout<<A[1]<<" ";
        swap(A[1],A[i]);//交互A[1]和A[i],使得A[i]中为当前最大的元素
        heapsize--;//堆大小减去1,便于下次操作去掉已经排好序的元素
        MaxheapFY(A,1);//此时A[1]不一定满足最大堆的性质,重新维护下标1的最大堆的性质
    }
}

/**
 *下面我们来讨论基于最大堆的实现的最大优先级队列
 *显然优先级队列是一种数据结构,我们知道任意一种数据结构都有其对应的操作(函数)
 *下面给出最大优先级队列对应的操作
 *1、PQueue_Insert(A,x):把元素x插入到集合S中,集合S对应的是一种最大优先级队列
 *2、PQueue_Maxnum(A):返回最大优先级队列S中,键值最大的元素
 *3、PQueue_Pop(A):去掉并返回最大优先级队列S最大键值的元素并删除
 *4、PQueue_IncresaseKey(A,x,key):将元素x的关键字的值增加到key(尽对应这里的最大优先级队列)
 *
 *特别注意:::
 *这里的优先级队列是基于最大堆建立的后,进行维护和操作的,因此在进行最大优先级队列
 *操作之前,必须先进行初始胡函数PQueue_Init(A,n):初始化长度为n集合S,构造成最大堆
 *
 */

void PQueue_Init(int *A,int n){
    BuildMaxHeap(A,n);//调用建立最大堆的函数进行初始化
}

int PQueue_Maxnum(int *A){
    return A[1];
}

int PQueue_Pop(int *A){
    if(heapsize>=1){
        int max=A[1];
        A[1]=A[heapsize];
        --heapsize;//堆大小(最大优先级队列的大小)减去1,
        MaxheapFY(A,1);//维护剩下的heaps的最大堆的性质
        return max;
    }
    else return -1;//删除失败
}
int PQueue_IncresaseKey(int *A,int i,int key){//增大A[i]的键值
    if(key<A[i]) return -1;//不符合最大堆的要求(仅仅是这里的定义)

    A[i]=key;//注意此时i的所有祖先都有可能不在满足最大堆的性质,
             //因此我们余姚判断所有的祖先是否满足最大堆的要求
    while(i>1&&A[PARENT(i)]<A[i]){
        swap(A[i],A[PARENT(i)]);
        i=PARENT(i);//向上判断到达当前的当前的结点满足最大堆的性质或者到达祖宗结点
    }
}

void PQueu_Insert(int *A,int key){
    //插入首先最大优先级队列的大小增加1
    ++heapsize;
    A[heapsize]=INF;//对新增的结点赋值一个永远娶不到的最小的值(仅对应于本程序的最大优先级队列)
    //剩下的操作就相当于将下标heapsize的关键字增大到key后,进行维护了,直接调用函数就好了
    PQueue_IncresaseKey(A,heapsize,key);

}

int main()
{
    int A[9]={0,4,2,5,6,2,6,1,7};

    /**
     *堆排序测试
     */
    Print(A,8);
    HeapSort(A,8);
    Print(A,8);


    /**
     *最大优先级队列测试
     */
    PQueue_Init(A,8);
    cout<<PQueue_Maxnum(A)<<endl;
    cout<<PQueue_Pop(A)<<endl;
    cout<<PQueue_Maxnum(A)<<endl;

    PQueue_IncresaseKey(A,5,10);

    PQueu_Insert(A,12);
    cout<<PQueue_Maxnum(A)<<endl;
    cout<<PQueue_Pop(A)<<endl;
    cout<<PQueue_Maxnum(A)<<endl;

    return 0;
}
图解算法:堆、堆排序、优先队列 堆、堆排序、优先队列可以看成就是一个东西;堆是一种非常重要的数据结构,堆排序是基于堆这种数据结构实现的;优先队列可以用堆这种数据结构来实现,也可以用其他数据结构实现。优先队列可以用来实现有优先级的任务调用(一些任务在池子里等待,优先级最高的先被优先取出执行) 阅读详情

相关推荐

数据结构中的堆:原理、实现与应用详解

System.out.println("添加 " + num + " 后,中位数: " + finder.findMedian());System.out.println("Top " + k + " 最大值: " + findTopKMax(nums, k));System.out.println("Top " + k + " 最小值: " + findTopKMin(nums, k));System.out.println("节点[" + i + "]=" + heap[i] +// 存储较小的一半。

ysct_999的博客 5030

【数据结构与算法】第九章:优先队列(最大、最小、索引)

普通的队列是一种先进先出的数据结构,元素在队列尾追加,而从队列头删除。在某些情况下,可能需要找出队列中的最大值或者最小值 例如:使用一个队列保存计算机的任务,一般情况下计算机的任务都是有优先级的,需要在这些计算机的任务中找出优先级最高的任务先执行,执行完毕后就需要把这个任务从队列中移除。普通的队列要完成这样的功能,需要每次遍历队列中的所有元素,比较并找出最大值,效率不是很高,这个时候,就可以使用一种特殊的队列来完成这种需求,优先队列 优先队列按照其作用不同,可以分为以下两种: 最大优先队列: .

土味儿 1466

[GXYCTF2019]BabyUpload1 -- .htaccess文件解析与蚁剑实战指南

本文深入解析了[GXYCTF2019]BabyUpload1文件上传漏洞的实战利用。通过绕过后缀名与内容检测,上传包含PHP代码的.jpg文件,并利用.htaccess文件强制服务器将其解析为PHP脚本。文章详细介绍了.htaccess的原理、构造方法、Content-Type绕过技巧,并演示了如何使用中国蚁剑连接Webshell获取Flag,为Web安全学习提供了完整实战指南。

weixin_29016315的博客 509

优先队列(详解--最大优先队列,最小优先队列)

优先队列 普通的队列是一种先进先出的数据结构,元素在队列尾部追加,从而队列头删除。在某些情况下,我们可能需要找出队列中的最大值或者最小值,例如使用一个队列保存计算机的任务,一般情况下,计算机的任务都是有优先级的,我们需要在这些计算机的任务中找出优先级最高的任务先执行,执行完毕后就需要把这个任务从队列中移除。普通的队列要完成这样的功能,需要每次遍历队列中的所有元素,比较并找出最大值,效率不是很高,这......

qq_43751200的博客 8509

国密https握手协议抓包及流程详解

使用的密码套件清单-Cipher Suite,这里服务器端选择了ECC_SM4_CBC_SM3密码套件,也就是SM2公钥算法、SM4-CBC分组密码算法和SM3杂凑算法。具体来说,这里SM2算法密钥交换算法,SM4是加密算法(SM4-CBC)、SM3是校验算法(国标要求为HMAC-SM3)。服务器的加密证书:加密证书中在同样在扩展字段中KeyUsage标识出KeyEncipherment为true和dataEncipherment为true,即数字证书中包含的公钥可用来做密钥加密密钥和数据密钥。

ryanzzzzz的博客 5847

SAP UI5 SimpleForm 的本质、布局选择与工程化用法:从 API 到 Fiori 规范的完整解析

SimpleForm的价值在于让开发者以“语义顺序”来思考表单:分组—行—字段,由此把更多精力放在表单信息架构与Fiori规范的落地上。当你理解了开分组、Label开新行、的断点与比例、的对齐特性、editable与的真实含义,就能据此为每个页面挑选合适的布局与参数,构建既合规又具备高可读性的企业级表单。新分组、Label新行、其他控件归当前行。SAP的断点、比例与的要点来自Fiori设计文档。SAP的适用性来自样例与课程的推荐,列表类控件不应作为其行内容。某些旧属性仅在生效,应避免误用。

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 301

数据结构——队列、最大堆、优先级队列

队列是一种只允许在一端进行插入操作,而在另一端进行删除操作的线性表。队列,顾名思义,就好像我们在超市结账排队一样,先排进队的人先买单,先进入队列里的元素先出队,也就是 先进先出的特点(First In First Out,FIFO),允许插入元素的一端称为队尾,允许删除元素的一端称为队首。

Se_ren_di_pity的博客 1914

CentOS7安装OpenSSL1.1.1s

CentOS7安装OpenSSL1.1.1s

Bertram的博客 733

堆与排序

数据结构与算法之美 28 | 堆和堆排序:为什么说堆排序没有快速排序快? 王争2018-11-26 堆排序是一种原地的,时间复杂度为O(nlogn)的排序算法 在美团一面中,问到了堆排序的手写,太久没有看堆排序,所以在这个环节错失良机. 堆是一个完全二叉树 堆中每一个节点的值都必须大与其子树的值 父节点的序号,与左右节点之间存在着关系 .parent *2+1=left...

搬砖的少年 229

Far planner 代码系列(14)

MatchContourWithNavGraph(3) this->EnclosePolygonsCheck(); //可能有些ctnode的is_contour_necessary属性变成了true // 这说明我的contour_graph是一个local层级的 才会从这里面 get new vertices new_convex_vertices.clear(); //! 把contour_graph_里符

博客 899

【Bug已解决】Codex 切换 model_provider 后历史会话消失的解决方案

方案适用场景推荐指数切回原 provider 验证排查的第一步,确认数据是否真的丢失⭐⭐⭐⭐⭐查看本地会话文件进一步确认数据完整性⭐⭐⭐⭐⭐查阅跨 provider 恢复命令官方是否提供了对应功能⭐⭐⭐使用社区辅助工具需要频繁切换 provider 的场景⭐⭐⭐定期备份配置目录任何场景下的通用保险措施⭐⭐⭐⭐切换后历史会话"消失"的本质是客户端的会话列表展示逻辑受当前活跃 provider 状态过滤,而不是原始数据文件被真正删除。

一键难忘的博客 5999

【原创】优先队列 priority_queue 详解

c++ 的 stl 里的 优先队列 priority_queue 的声明和基本操作

致上 19万+

VHDL语法学习笔记:一文掌握VHDL语法

今天给大侠带来FPGA 之 VHDL 语法学习笔记,话不多说,上货。 VHDL语法学习笔记 一、VHDL简介 1.1 VHDL 的历史 VHDL 的 英 文 全 名 是 Very-High-Speed Integrated Circuit Hardware DescriptionLanguage,诞生于 1982 年。 1987 年底,VHDL 被 IEEE 和美国国防部确认为标准硬件描述语言。自 IEEE 公布了 VHDL 的标准版本 IEEE-1076(简称 87 版)...

2万+

C++数据结构详解——堆

1.堆的原理精讲 最大堆特点: 当然,也有最小堆,最小堆就是将最大堆反过来,根结点为最小值~ 堆是树中最有个性的树,他是用数组表示的树 。 2.在数组中快速创建堆算法 1.首先我们需要找到最后一个结点的父结点如图(a),我们找到的结点是 87,然后找出该结点的最大子节点与自己比较,若该子节点比自身大,则将两个结点交换。 图(a)中,87 比左子节点 95 小,则交换之。如图(b)所示 2.我们移动到第一步前一个父节点 93,如图(c)所示.同理做第一步的比较...

qq_54169998的博客 1万+

李航《统计学习方法》课后习题答案(第2版)

李航《统计学习方法》课后习题答案(第2版) 章节 链接 第1章 统计学习及监督学习概论 点击进入 第2章 感知机 点击进入 第3章 k近邻法 点击进入 第4章 朴素贝叶斯法 点击进入 第5章 决策树 点击进入 第6章 逻辑斯谛回归与最大熵 点击进入 第7章 支持向量机 点击进入 第8章 提升方法 点击进入 第9章 EM算法及其推广 点击进入 第10章 隐马尔可夫模型 点击进入 第11章 条件随机场 点击进入     也可进入我的个人主页查看分类专栏

weixin_43646592的博客 2万+

Data-Structures-and-Algorithm-Analysis-in-Java.pdf

作者: Weiss, Mark A. 出版社: Addison Wesley Data Structures and Algorithm Analysis in Java is an “advanced algorithms” book that fits between traditional CS2 and Algorithms Analysis courses. In the old ACM Curriculum Guidelines, this course was known as CS7. This text is for readers who want to learn good programming and algorithm analysis skills simultaneously so that they can develop such programs with the maximum amo...

堆的实现以及堆排序(最大堆,最小堆)

1.堆的概念 堆是一种特殊的数据结构,相当于数组实现的一颗二叉树,但是和一般的二叉搜索树不同 1.堆分为最大堆(父结点不小于其孩子结点)和最小堆(父结点不大于其孩子结点),分别表示 最大堆和最小堆只是>和 < 的关系 template<typename T> class ...

qq_42584241的博客 913

迈瑞BS系列全自动生化分析仪LIS协议接口手册(内含HL7和ASTM)

迈瑞BS系列全自动生化分析仪LIS协议接口手册,内含HL7和ASTM)

【算法】4 五张图带你体会堆算法

什么是堆堆(heap),是一类特殊的数据结构的统称。它通常被看作一棵树的数组对象。在队列中,调度程序反复提取队列中的第一个作业并运行,因为实际情况中某些时间较短的任务却可能需要等待很长时间才能开始执行,或者某些不短小、但很重要的作业,同样应当拥有优先权。而堆就是为了解决此类问题而设计的数据结构。二叉堆是一种特殊的堆,二叉堆是完全二叉树或者近似完全二叉树,二叉堆满足堆特性:父节点的键值总是保持固定的序

nomasp 1万+

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

堆的实现以及相关应用(堆排序、优先队列)——基于Python

堆实现 #------------------------------------------------------------------------------ #堆Heap #------------------------------------------------------------------------------ import sys class Heap(): def __init__(self, A: list): self.A = A

wangchang1314的博客 315

排序(3) 堆与堆排序

堆,堆排序,优先队列,经典问题

Lurfee的博客 829

二叉堆(最小堆, 最大堆)介绍与实现

二叉堆是一种特殊的二叉树, 它总是保证一棵树的最小元素(最小堆)或者最大元素(最大堆)处于树根上, 常见的应用场景就是用于构建优先队列, 在jdk中Doug Lea所实现的ScheduledThreadPoolExecutor中就是用到了最小堆; 二叉堆介绍 二叉堆的编程实现 应用场景 二叉堆介绍 什么是树? 计算机中树是一种数据结构(有向无环图), 因为它看起来像一颗倒挂的树, 所以被称为树...

江无羡 1万+

php+堆排序算法,PHP面试:说下什么是堆和堆排序?

堆是什么?堆是基于树抽象数据类型的一种特殊的数据结构,用于许多算法和数据结构中。一个常见的例子就是优先队列,还有排序算法之一的堆排序。这篇文章我们将讨论堆的属性、不同类型的堆以及堆的常见操作。另外我们还将学习堆排序,并将使用SPL实现堆。根据定义,堆是一个拥有堆特性的树形数据结构。如果父节点大于子节点,那么它被称为最大堆,如果父节点小于子节点,则称为最小堆。下图是最大堆的例子我们看根节点,值100...

weixin_30854435的博客 234

数据结构之堆

在计算机科学中,堆(Heap)是一种特殊的数据结构,它是一种完全二叉树(或者近似完全二叉树),并且满足堆属性。堆有两种常见的类型:最大堆(Max Heap)和最小堆(Min Heap)。最大堆中,父节点的值大于或等于其子节点的值,而最小堆中,父节点的值小于或等于其子节点的值。堆的主要特点是根节点(顶部节点)具有最大(或最小)值。这使得堆在很多应用中非常有用,例如优先队列和堆排序算法。堆的实现可以使用数组或者链表来表示。在数组实现中,根节点存储在索引位置0,而子节点的索引位置可以通过简单的计算得到。

m0_69767208的博客 594

【数据结构】什么是堆

1、堆的定义:堆是一个完全二叉树,每个节点的值与其子节点的值具有特定的关系(最大堆或最小堆)。插入(Insert):将新元素插入堆中,并维护堆的性质。删除最大/最小元素(Extract-Max/Min):删除堆中的最大元素(在最大堆中)或最小元素(在最小堆中),并重新调整堆以维持其性质。堆化(Heapify):调整堆的结构,使其符合堆的性质。构建堆(Build-Heap):将一个无序数组转化为一个堆。

联系方式:927632640 465

堆、堆排序与优先队列

堆、堆排序与优先队列 堆(heap)   堆(Heap)是计算机科学中一类特殊的数据结构。堆通常用数组来实现。把堆近似看作一棵完全二叉树(最底层可能不是完全填满的,如下图),堆中结点的值总是不大于或不小于其父结点的值。   根结点最大的堆叫做最大堆或大根堆。   根结点最小的堆叫做最小堆或小根堆。   最小堆示例:   表示堆的数组AAA有两个属性:A.lengthA.lengthA.lengt...

未见君子,忧心如醉 233

【堆】建堆、插入、删除、堆排序

参考 堆就是利用数组来实现二叉树,可用于构建优先队列、堆排序、TopK问题等。可分为: 最大堆:父节点的值比其子节点大 最小堆:父节点的值比其子节点小 堆的根节点存放了最小(或最大)元素,但是其它节点的排序是未知的,即左节点不一定比右节点大(或小),堆的搜索相对于二叉搜索树更慢,二叉搜索树(如AVL)是平衡二叉树,搜索时间复杂度为O(nlogn),而堆的目的只是为了获得最大(或最小)元素,将其存储在头节点。 实现堆只需要一个顺序存储结构的数组,相对于二叉树而言,空间开销更低,二叉树还需要分配左右指针占用

这个人很蓝 593

【数据结构篇】堆

本文主要是对堆的一个简单介绍,如果你是刚学数据结构的话,十分推荐看这篇文章,通过本文你将对堆这个数据结构有一个大致的了解,同时学习JDK自带的堆实现类类,如何基于数组手写一个堆。什么是堆?堆(Heap)是一种常见的数据结构,堆可以基于数组实现,也可以基于链表实现。堆的定义如下:n个元素的序列k1k2kiknk1k2kikn当且仅当满足下关系kik2ikik2i1ki

热爱编程、热爱生活、热爱探索 1208
上一篇: 计数排序+基数排序
下一篇: 桶排序实现(没有优化)
xiaoranone
博客等级 码龄13年 156粉丝 258原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值