一、大顶堆和小顶堆的原理

1、大顶堆

  • 根结点(亦称为堆顶)的关键字是堆里所有结点关键字中最大者,称为大顶堆。大根堆要求根节点的关键字既大于或等于左子树的关键字值,又大于或等于右子树的关键字值。

2、小顶堆

  • 根结点(亦称为堆顶)的关键字是堆里所有结点关键字中最小者,称为小顶堆。小根堆要求根节点的关键字既小于或等于左子树的关键字值,又小于或等于右子树的关键字值。

3、大顶推和小顶堆的实现

public class MaxHeap {public static void main(String[] args) {//原始数组内容int i,size,data[]={0,5,6,10,8,3,2,19,9,11};size=data.length;System.out.print("原始数组:");for(i=1;i<size;i++)System.out.print("["+data[i]+"] ");System.out.println("");//建立堆积树MaxHeap.heap(data,size);}public static void heap(int data[] ,int size){int i,j,tmp;//建立堆积树节点for(i=(size/2);i>0;i--)MaxHeap.ad_heap(data,i,size-1);System.out.print("\n堆积内容:");//原始堆积树内容for(i=1;i<size;i++)System.out.print("["+data[i]+"] ");}public static void ad_heap(int data[],int i,int size){int j,tmp,post;j=2*i;tmp=data[i];post=0;while(j<=size && post==0){if(j<size){//小顶堆的比较           //if(data[j]>data[j+1])  //找出两个子节点最大值if(data[j]<data[j+1])  j++;}//小顶堆的比较//if(tmp<=data[j])   //若树根较大,结束比较过程if(tmp>=data[j])    {post=1;  } else {//若树根较小,则继续比较,这里将最大子节点赋值给父节点data[j/2]=data[j];     j=2*j;}}//指定树根为父节点data[j/2]=tmp;                }
}

二、小顶堆的应用

1、求最大的k个数

  • 1、求10亿个数中的最大的前10个数,时时构建只有10个元素的小顶堆,如果比堆顶小,则不处理;如果比堆顶大,则替换堆顶,然后依次下沉到适当的位置。 详细讲解请看公众号:码农有道
  • 2、选择最大的K个数
public class findTopK {//用PriorityQueue默认是自然顺序排序,要选择最大的k个数,构造小顶堆,每次取数组中剩余数与堆顶的元素进行比较,如果新数比堆顶元素大,则删除堆顶元素,并添加这个新数到堆中。//找出前k个最大数,采用小顶堆实现public static int[] findKMax(int[] nums, int k) {//队列默认自然顺序排列,小顶堆,不必重写comparePriorityQueue<Integer> pq = new PriorityQueue<>(k);for (int num : nums) {if (pq.size() < k) {pq.offer(num);//如果堆顶元素 < 新数,则删除堆顶,加入新数入堆} else if (pq.peek() < num) {pq.poll();pq.offer(num);}}int[] result = new int[k];for (int i = 0; i < k&&!pq.isEmpty(); i++) {result[i] = pq.poll();}return result;}public static void main(String[] args) {int[]arr=new int[]{1, 6, 2, 3, 5, 4, 8, 7, 9};System.out.println(Arrays.toString(findKMax( arr,5)));}
}

2、数组中的第K个最大元素

 // 小顶堆PriorityQueue<Integer> pq = new PriorityQueue<>();for (int val : nums) {pq.add(val);// 维护堆的大小为 Kif (pq.size() > k) {//弹出最顶端的数,并删除pq.poll();}}//取最顶端的数return pq.peek();}

三、大顶堆的应用

  • PriorityQueue通过传入自定义的compara函数可以实现大顶堆

1、要选择最小的K个数使用大顶堆,每次取数组中剩余数与堆顶的元素进行比较,如果新数比堆顶元素小,则删除堆顶元素,并添加这个新数到堆中。

public static int[] findKMin(int[] nums,int k ){PriorityQueue<Integer> pq = new PriorityQueue<>(k, new Comparator<Integer>() {@Overridepublic int compare(Integer o1, Integer o2) {return o2 - o1;}});for (int num:nums){if (pq.size() <k){pq.offer(num);//如果堆顶元素 > 新数,则删除堆顶,加入新数入堆}else if(pq.peek() > num){pq.poll();pq.offer(num);}}int[] result = new int[k];for (int i = 0;i<k&&!pq.isEmpty();i++){result[i] = pq.poll();}return result;}public static void main(String[] args) {int[]arr=new int[]{1, 6, 2, 3, 5, 4, 8, 7, 9};System.out.println(Arrays.toString(findKMin( arr,5)));}

2、数组中的第K个最小元素

   public static int findKthLargest(int[] nums, int k) {PriorityQueue<Integer> pq = new PriorityQueue<>(k, new Comparator<Integer>() {@Overridepublic int compare(Integer o1, Integer o2) {return o2 - o1;}});for (int val : nums) {pq.add(val);// 维护堆的大小为 Kif (pq.size() > k) {pq.poll();}}return pq.peek();}

大顶堆和小顶堆-java相关推荐

  1. 用Java实现二叉堆、大顶堆和小顶堆

    先了解了解 什么是二叉堆 二叉堆就是完全二叉树,或者是靠近完全二叉树结构的二叉树.在二叉树建树时采取前序建树就是建立的完全二叉树.也就是二叉堆.所以二叉堆的建堆过程理论上讲和前序建树一样. 什么是大顶 ...

  2. 堆排序:大顶堆和小顶堆 + 前K个高频元素

    堆 一.堆排序 小顶堆 举个栗子 大顶堆 二.前K个高频元素 思路分析 三.构造器代码解析 一.堆排序 要了解大顶堆和小顶堆,我们先简单了解一下堆排序. 堆排序(Heapsort)是指利用堆这种数据结 ...

  3. 【tree】二叉堆(大顶堆或小顶堆)

    本文目录 一.二叉堆的定义 结构性质 堆序性质 二.二叉堆的底层存储结构 三.二叉堆的插入 四.二叉堆的删除 五.源码和测试 系列目录 <树> <树的遍历> <二叉查找树 ...

  4. 堆排序之 大顶堆和小顶堆 c语言

    百度得到的堆定义如下: 堆的定义如下:n个元素的序列{k1,k2,ki,-,kn}当且仅当满足下关系时,称之为堆. (ki <= k2i,ki <= k2i+1)或者(ki >= k ...

  5. 谈谈堆排序,大顶堆,小顶堆

    目录 1.前言 2.使用堆的原因 3.堆的特点 4.堆和普通树的区别 5.堆排序的过程 6.堆排序的代码实现 来源: jianshu.com/p/15a29c0ace73 1.前言 堆是一种非线性结构 ...

  6. NO29、最小的K个数(应该记住大顶堆和小顶堆的区别与联系,并不难)

    29.最小的K个数 应该记住大顶堆和小顶堆的区别与联系,并不难 输入n个整数,找出其中最小的K个数.例如输入4,5,1,6,2,7,3,8这8个数字,则最小的4个数字是1,2,3,4,. 示例1 输入 ...

  7. C++大顶堆和小顶堆

    C++大顶堆和小顶堆 原理 大顶堆 小顶堆 大顶堆和小顶堆对比图 大顶堆和小顶堆的实现代码 vector和push_heap.pop_heap实现堆 建堆 调整堆 priority_queue实现堆 ...

  8. 堆排序(浅谈大顶堆与小顶堆)

    什么是堆? 堆是一种非线性结构,(本篇随笔主要分析堆的数组实现)可以把堆看作一个数组,也可以被看作一个完全二叉树,通俗来讲堆其实就是利用完全二叉树的结构来维护的一维数组,按照堆的特点可以把堆分为大顶堆 ...

  9. c语言标准模板小顶堆,堆排序(大顶堆、小顶堆)----C语言

    堆排序 之前的随笔写了栈(顺序栈.链式栈).队列(循环队列.链式队列).链表.二叉树,这次随笔来写堆 1.什么是堆? 堆是一种非线性结构,(本篇随笔主要分析堆的数组实现)可以把堆看作一个数组,也可以被 ...

最新文章

  1. golang 调用c代码
  2. 【Android】Vitamio 4.0 公测版发布(2013-05-28)
  3. DataScience:深入探讨与分析机器学习中的数据处理之非线性变换—log对数变换、sigmoid/softmax变换
  4. VIO在走廊弱纹理环境下的优化——VINS-Mono的点线紧耦合优化
  5. 爬虫笔记:pyquery详解
  6. lenze变频器怎么更改地址_英威腾变频器GD300维修
  7. Strategy 策略模式
  8. 应用交付脚本工具在HTTP服务中的应用
  9. android 8字体下载,安卓手机字体
  10. 7-4 换硬币(20 分)
  11. 谨慎处理单片机中断,中断等价于比主程序优先级更高的线程
  12. 打开Visual Studio Community 2017 报出“许可证已过期”
  13. android开发技巧精髓一
  14. 薛定谔的猫量子计算机,亚马逊新的量子计算机设计竞依赖于微小的“薛定谔的猫”...
  15. Cesium空间分析-填挖方计算
  16. 学校举办朗诵比赛,邀请了10位评委为每一名参赛选手的表现打分,打分由random库中的随机函数进行,打分范围在[80,100]之间,打分的结果存放在列表lst_score中。编写程序,根据以下规则计算
  17. 植物大战僵尸中文年度版
  18. Java Security Architecture--Java安全体系技术文档翻译(三)
  19. VASP 5.4.4 保姆级安装全过程 (附带vaspkit)
  20. FCPX超级慢动作变速插件Twixtor Pro 7 Mac破解版激活教程

热门文章

  1. Android之集成万能播放器Vitamio
  2. 【css】CSS 如何画两边是半圆的长方形?
  3. C51外扩6264芯片在proteus下的仿真
  4. 设计模式之单例(Singleton)
  5. 蒸汽平台进dota2显示连接不上服务器,关于DOTA2接入蒸汽平台的常见问题
  6. 新一期ARM作业(七)----Nand Flash
  7. 命令提示符-常用命令
  8. 联想小新310安装Windows11
  9. python论坛签到_吾爱论坛签到脚本-python
  10. 不让safari浏览器下载的Excel文件添加.exe后缀