一、实验名称:Array Implementation of min-Heaps

二、实验目的:
4. 熟练掌握最小堆的数据结构,结构的特点;
5. 能够实现最小堆的基本操作:如构造,插入,删除,初始化,回收内存等
三、实验内容:

A complete min-heap is a min-heap with the structure of a complete binary tree which can be stored using an array.

  1. Determine the array structures for a complete min-heap(以数组形式表示的树结构)
  2. Input a linear list of 20 random numbers, building a complete min-heap to store the numbers
  3. Implement POP and PUSH operations for the min-heaps.

四. 算法实现:
通过在堆的末尾添加或删除,插入和删除操作都首先修改堆以使其符合shape属性。然后,通过向上或向下遍历堆来恢复堆属性。两种操作都需要O(log n)时间。
1.插入
要将元素添加到堆,我们可以执行以下算法:

将元素添加到堆的最底层开放空间的最底层。
将添加的元素与其父元素进行比较;如果顺序正确,请停止。
如果不是,则将元素与其父元素交换并返回上一步。
步骤2和3通过比较节点并可能与其父节点交换节点来恢复堆属性,这些步骤称为up-heap操作。

所需的操作数仅取决于新元素必须满足堆属性的级别数。因此,插入操作的最坏情况时间复杂度为O(log n)。对于随机堆和重复插入,插入操作的平均情况复杂度为O(1)。
2.弹出
从堆中删除根的过程(有效地提取max-heap中的最大元素或min-heap中的最小元素),同时保留heap属性:

用最后一级的最后一个元素替换堆的根。
将新的根与其子代进行比较;如果顺序正确,请停止。
如果不是,则将元素与其子元素之一交换并返回上一步。(将其较小的子项换成最小堆,将其较大的子项换成最大堆。)
步骤2和3通过将节点与子节点之一进行比较并可能与其交换来恢复堆属性,这些步骤称为下降堆操作

3.建立堆
从最低级别开始向上移动,像删除算法一样向下筛选每个子树的根,直到恢复堆属性。

四. 程序清单(较为详细的注释):

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define MaxSize 100
typedef struct Hnode* MinHeap;
struct Hnode{int* data;int size;int Capacity;
};
int getRandomNum(){int RandomNum;RandomNum=rand();return  RandomNum;
}
/*Filter down and find the proper position of the node on the premise that all subtrees are the smallest heap.
The tree with this node as the root node is a smallest heap*/
void FixDown(MinHeap h,int index){int parent;int child;int temp=h->data[index];for(parent=index;parent*2<=h->size;parent=child){child=parent*2;if(child+1<=h->size&&h->data[child+1]<h->data[child])child++;if(h->data[child]<temp){h->data[parent]=h->data[child];}else break;}h->data[parent]=temp;
}
/*The idea of recursion is adopted to establish the minimum heap from bottom to top, which ensures
that the subtrees currently established are all the smallest heaps.*/
void BuildMinHeap(MinHeap h){int i;for(i=h->size/2;i>=1;i--){FixDown(h,i);}
}
//Determine whether the MinHeap is empty
int Empty(MinHeap h){return h->size==0;
}
//Return and delete the minimum value of the minimum heap (that is, the head node), and keep the tree as the minimum heap
/*Move the last node to the head node, and size--,
Because the subtrees are all the smallest heap at this time, filtering directly
down can ensure that the tree is still the smallest heap*/
int PopMinHeap(MinHeap h){if(Empty(h)){printf("The minimum heap is empty, and the popped -11111 is an invalid value\n");return -11111;}int result=h->data[1];h->data[1]=h->data[(h->size)--];//向下过滤FixDown(h,1);return result;
}
/*Insert node, keep minimum heap*/
void PushMinHeap(MinHeap h,int val){if(h->size==h->Capacity){printf("The minimum heap is full and element insertion is invalid\n");return;}h->data[++(h->size)]=val;//向上过滤int child=h->size;int parent;for(;child>1;child=parent){parent=child/2;if(h->data[parent]>val){h->data[child]=h->data[parent];}else{break;}}h->data[child]=val;
}
/*Request space for the MinHeap*/
MinHeap CreateMinHeap(int MinHeapSize){MinHeap h=(MinHeap)malloc(sizeof(MinHeap));h->data=(int*)malloc((MinHeapSize+1)*sizeof(int));h->size=0;h->Capacity=MinHeapSize;return h;
}
/*Free up space for MinHeap*/
void CleanMinHeap(MinHeap h){free(h->data);free(h);
}
int main()
{MinHeap h=CreateMinHeap(MaxSize);//Construct the MinHeap with a random array of 20 numbers, and pop the MinHeap number in turnprintf("Construct the MinHeap with a random array of 20 numbers\n");srand((unsigned)time(NULL));int i=1;printf("20 random numbers:\n");for(;i<=20;i++){h->data[i]=getRandomNum();printf("%d ",h->data[i]);h->size++;}printf("\n");BuildMinHeap(h);//After the minimum heap is established, pop the elementprintf("After the minimum heap is established, pop the element:\n");while(!Empty(h)){printf("%d ",PopMinHeap(h));}printf("\n");//Randomly insert 10 elementsint randNum;printf("10 random numbers inserted in sequence:\n");for(i=1;i<=10;i++){randNum=getRandomNum();printf("%d ",randNum);PushMinHeap(h,randNum);}printf("\n");//while the minimum heap is not empty, pop the elementprintf("After the insertion, pop the element:\n");while(!Empty(h)){printf("%d ",PopMinHeap(h));}printf("\n");CleanMinHeap(h);return 0;
}

五、测试结果:

输入输出格式说明:

  • 输入格式:

  • 输出格式:
    先输出20个随机数组的内容;
    再输出数组构造的最小堆,依次弹出的内容;
    再输出10个依次插入的随机;
    再依次插入后的最小堆,依次弹出的内容;

  • 测试样例1:

    输入:

    输出:

    Construct the MinHeap with a random array of 20 numbers
    20 random numbers:
    25934 30979 23498 31152 11647 2301 29550 22606 11334 6914 30615 28013 5979 11444 21228 3691 28332 32284 17894 14376
    After the minimum heap is established, pop the element:
    2301 3691 5979 6914 11334 11444 11647 14376 17894 21228 22606 23498 25934 28013 28332 29550 30615 30979 31152 32284
    10 random numbers inserted in sequence:
    16559 5286 28109 18979 2294 28525 14307 31967 23812 20665
    After the insertion, pop the element:
    2294 5286 14307 16559 18979 20665 23812 28109 28525 31967
    
  • 测试样例2:

    输入:

    输出:

    Construct the MinHeap with a random array of 20 numbers
    20 random numbers:
    26012 26797 26254 18847 29821 31007 5944 17888 14396 23200 27065 29070 13024 15340 29552 26589 16604 15737 29064 21912
    After the minimum heap is established, pop the element:
    5944 13024 14396 15340 15737 16604 17888 18847 21912 23200 26012 26254 26589 26797 27065 29064 29070 29552 29821 31007
    10 random numbers inserted in sequence:
    28387 16381 28017 23489 25085 31792 1424 1400 1499 18387
    After the insertion, pop the element:
    1400 1424 1499 16381 18387 23489 25085 28017 28387 31792
  • 测试样例3:

    输入:

    输出:

    Construct the MinHeap with a random array of 20 numbers
    20 random numbers:
    26058 13435 14208 28054 10385 20445 16751 9674 16182 2663 24995 29686 28056 17613 12562 7179 31608 11546 21926 23578
    After the minimum heap is established, pop the element:
    2663 7179 9674 10385 11546 12562 13435 14208 16182 16751 17613 20445 21926 23578 24995 26058 28054 28056 29686 31608
    10 random numbers inserted in sequence:
    24364 3738 8848 23389 151 22775 4832 2683 10328 8866
    After the insertion, pop the element:
    151 2683 3738 4832 8848 8866 10328 22775 23389 24364
    
  • 测试样例4:

    输入:

    
    

    输出:

    Construct the MinHeap with a random array of 20 numbers
    20 random numbers:
    26133 31272 31868 24454 18244 12456 22801 7883 2733 25098 21593 30699 12962 4962 31462 12739 25829 9342 31264 7589
    After the minimum heap is established, pop the element:
    2733 4962 7589 7883 9342 12456 12739 12962 18244 21593 22801 24454 25098 25829 26133 30699 31264 31272 31462 31868
    10 random numbers inserted in sequence:
    24777 32119 26509 20885 8339 14983 3408 21176 10790 18970
    After the insertion, pop the element:
    3408 8339 10790 14983 18970 20885 21176 24777 26509 32119

六、算法分析:
最小堆的插入和删除操作都是在树的结构基础上建立的,每次的时间复杂度为O(log n)时间,
若算法需要n次插入,每次删除,则插入和删除总共的时间复杂度为O((n+m)log n);
构造有n个节点的最小堆,同理其时间复杂度为O(nlog n);
算法的空间复杂度为最小堆数据结构(以数组形式表示的树结构)的内存空间

Array Implementation of min-Heaps 最小堆数组实现相关推荐

  1. 最大堆和最小堆和平衡二叉树_最小堆二叉树

    最大堆和最小堆和平衡二叉树 A Min Heap Binary Tree is a Binary Tree where the root node has the minimum key in the ...

  2. Leetcode215数组中第k大的数-最小堆

    题目 在未排序的数组中找到第 k 个最大的元素.请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素. 示例 1: 输入: [3,2,1,5,6,4] 和 k = 2 输出 ...

  3. 二叉堆(最小堆)(数据结构与算法分析的代码实现)

    "堆是一棵被完全填满的二叉树,可能的例外是在底层,底层上的元素从左到右填入.这样的树称为完全二叉树" "因为完全二叉树很有规律,所以可以用一个数组表示而不需要使用链&qu ...

  4. 最小堆解决Top K问题

    问题描述: 有一组数据n个,要求取出这组数据中最大的K个值. 对于这个问题,解法有很多中.比如排序及部分排序,不过效率最高的要数最小堆,它的时间复杂度为O(nlogk). 解题思路: 取出数组的前n个 ...

  5. 使用最大堆和最小堆实现中位数的查找

    参考链接:双堆维护数组中位数 用堆维护中位数的意思是说,设计两个堆,第一个堆(大顶堆)存放小于中位数的元素,第二个堆(小顶堆)存放大于中位数的元素. 下面是双堆维护中位数的语言描述: 1.初始化的时候 ...

  6. Python - 最小堆实现与应用

    一.引言 前面写到了 最大堆的实现应用,趁热打铁把最小堆的也搞定,最小堆一定意思上和最大堆的实现相同,这不过"大"的概念变成了"小",不同认知下,可以理解为两个 ...

  7. 数据结构与算法--二叉堆(最大堆,最小堆)实现及原理

    二叉堆(最大堆,最小堆)实现及原理 二叉堆与二叉查找树一样,堆也有两个性质,即结构性质和堆性质.和AVL树一样,对堆的一次操作必须到堆的所有性质都被满足才能终止,也就是我们每次对堆的操作都必须对堆中的 ...

  8. 使用最小堆使用优先级队列(c语言版本)

    下面的例子来自Weiss的<数据结构与算法分析:c语言描述>,自己亲自敲了一遍,跑了个demo,并将结果记录下来. binheap.h的头文件声明 //description: 使最小堆实 ...

  9. Java实现最小堆一

    2019独角兽企业重金招聘Python工程师标准>>> Java实现最小堆一 堆是一种经过排序的完全二叉树,其中任一非终端节点的数据值均不大于(或不小于)其左孩子和右孩子节点的值. ...

  10. 优先级队列 c语言,使用最小堆使用优先级队列(c语言版本)

    下面的例子来自Weiss的<数据结构与算法分析:c语言描述>,自己亲自敲了一遍,跑了个demo,并将结果记录下来. binheap.h的头文件声明 //description: 使最小堆实 ...

最新文章

  1. CF1030F Putting Boxes Together
  2. javascript showModalDialog,open取得父窗口的方法
  3. 哇塞!给 IDEA 换个酷炫的主题
  4. 二零一三年计算机视觉代码合集
  5. python输出姓名年龄_Python格式化输出--%s,%d,%f的代码解析
  6. Python——科赫曲线绘制
  7. 整数翻转Python解法
  8. Java多线程(2)--Thread类继承和Runnable接口创建线程
  9. 【CodeForces - 1020A】New Building for SIS(模拟)
  10. 太阳能板清洗机器人科沃斯_太阳能电池板清洁机器人
  11. 手机端测试时用的几个软件
  12. 数组的冒泡排序快速上手
  13. 6.1 API : AdaBoostClassifier与AdaBoostRegressor
  14. 汽车常识全面介绍 - 刹车系统
  15. 微信授权就是这个原理,Spring Cloud OAuth2 授权码模式
  16. Ubuntu Linux DNS服务器 BIND9配置文件命令介绍
  17. 计算机无法安装u盘驱动,电脑上插入u盘提示未能成功安装设备驱动程序怎么修复...
  18. HoloLens开发学习笔记(一):HoloLens简介
  19. VS无法打开项目文件“Web.csproj” -此安装不支持该项目类型问题解决方案
  20. ECCV 2022 | 超越MobileViT!EdgeFormer:学习ViT来改进轻量级卷积网络

热门文章

  1. java gc 命令_Java 查看系统GC命令介绍
  2. 从“阿里月饼门”看安全
  3. word中 插入公式及交叉引用
  4. Macbook Pro Air锁屏不进入睡眠
  5. 树莓派4B-连接Air720U模块抓取数据日志
  6. java se检查异常,JavaSE:异常(下)
  7. 在Delphi程序中访问报表对象
  8. npm install 设置缓存
  9. ps做手机计算机界面,用PS制作手机UI界面设计
  10. android音乐加速软件,音乐变速器app