向上调整建堆与向下调整建堆的时间复杂度 AND TopK问题

目录

  • 前言
  • 建堆的时间复杂度
  • TOPK问题
  • 总结

前言

本篇旨在介绍使用向上调整建堆与向下调整建堆的时间复杂度. 以及topk问题

博客主页: 酷酷学!!!
感谢关注~

建堆的时间复杂度

堆排序是一种优于冒泡排序的算法, 那么在进行堆排序之前, 我们需要先创建堆, 为什么说堆排序的是优于冒泡排序的呢? 那么这个建堆的时间复杂度是多少呢?

void HeapSort(int* a, int n)
{//降序//创建小堆//向下调整创建,从最有一个非叶子节点//时间复杂度O(N)for (int i = (n-1-1)/2; i>=0; i--){Adjustdown(a, n, i);}//堆创建之后,交换第一个节点与最后一个节点,//时间复杂度为O(N*logN)int end = n-1;while (end > 0){Swap(&a[0], &a[end]);Adjustdown(a, end, 0);end--;}
}

首先来看向下调整算法建堆的时间复杂度, 因为堆是完全二叉树,而满二叉树也是完全二叉树,此处为了简化使用满二叉树来证明(时间复杂度本来看的就是近似值,多几个结点不影响最终结果):

假设高度为h的二叉树, 结点的个数为N, 可以计算出高度h与结点个数之间的关系如下图所示:

在这里插入图片描述

向下调整算法, 从最后一个非叶子结点开始向下调整, 也就是第h-1层, 需要向下移动一层, 第h-2层需要向下移动2层, … , 第一层则需要向下移动h-1层, 第二层的结点需要向下移动h-2层. 依次类推, 如图所示.
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
可以看出节点数量多的层调整次数少, 结点数量少的层调整次数多 . 错位相减法则可以计算出T(N) = 2^h - 1 - h, 带入h与N的关系则得出向下调整建堆的时间复杂度为O(N).

void Heapsort(int* a,int n)
{//时间复杂度为O(N*logN)for (int i = 1; i < n; i++){AdjustUP(a, i);}//时间复杂度为O(N*logN)int end = n - 1;while (end > 0){Swap(&a[0], &a[end]);AdjustDown(a, end, 0);end--;}
}

使用向上调整建堆, 计算其时间复杂度, 如下

在这里插入图片描述
总计调整次数为
在这里插入图片描述
使用错位相减法计算:

在这里插入图片描述
可以看出结点数多的层, 调整次数也多, 结点数少的层, 调整次数少, 时间复杂度为O(N*logN), 所以一般建堆都采用向下调整建堆法.

TOPK问题

TOP-K问题:即求数据结合中前K个最大的元素或者最小的元素,一般情况下数据量都比较大。
比如:专业前10名、世界500强、富豪榜、游戏中前100的活跃玩家等。
对于Top-K问题,能想到的最简单直接的方式就是排序,但是:如果数据量非常大,排序就不太可取了(可能数据都不能一下子全部加载到内存中)。最佳的方式就是用堆来解决,基本思路如下:

  1. 用数据集合中前K个元素来建堆

前k个最大的元素,则建小堆
前k个最小的元素,则建大堆

  1. 用剩余的N-K个元素依次与堆顶元素来比较,不满足则替换堆顶元素

将剩余N-K个元素依次与堆顶元素比完之后,堆中剩余的K个元素就是所求的前K个最小或者最大的元素。

例如: 求十万个数据中最大的前K个数, 要求只有1kb内存, 这些数据存储在磁盘中

首先先用前k个数建一个小堆, 剩下的N-K个元素依次与堆顶元素进行比较, 如果大于堆顶元素, 则替换堆顶元素, 并且向下调整堆, 结束后, 堆中数据即最大的k个元素.

代码如下:

第一步先使用随机数生成十万个数据

void CreateNDate()
{// 造数据int n = 100000;srand(time(0));const char* file = "data.txt";FILE* fin = fopen(file, "w");if (fin == NULL){perror("fopen error");return;}for (int i = 0; i < n; ++i){int x = (rand()+i) % 10000000;fprintf(fin, "%d\n", x);}fclose(fin);
}

读取数据, 并且用前k个数据创建一个小堆, 然后读取剩下的数据, 如果比堆顶数据大, 就替代堆顶数据进入堆, 然后向下调整堆.

void TestHeap()
{int k;printf("请输入k>:");scanf("%d", &k);int* kminheap = (int*)malloc(sizeof(int) * k);if (kminheap == NULL){perror("malloc fail");return;}const char* file = "data.txt";FILE* fout = fopen(file, "r");if (fout == NULL){perror("fopen error");return;}// 读取文件中前k个数for (int i = 0; i < k; i++){fscanf(fout, "%d", &kminheap[i]);}// 建K个数的小堆for (int i = (k-1-1)/2; i>=0 ; i--){AdjustDown(kminheap, k, i);}// 读取剩下的N-K个数int x = 0;while (fscanf(fout, "%d", &x) > 0){if (x > kminheap[0]){kminheap[0] = x;AdjustDown(kminheap, k, 0);}}printf("最大前%d个数:", k);for (int i = 0; i < k; i++){printf("%d ", kminheap[i]);}printf("\n");
}
int main()
{CreateNDate();TestHeap();return 0;
}

总结

建堆的时间复杂度为O(N), 使用堆排序的时间复杂度为O(N*logN), 而使用冒泡排序的时间复杂度为O(N^2), 故堆排序的效率明显高于冒泡排序, 而topk则解决了使用较小内存而求取一堆数据中最大或者最小的前k个数据.

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2023年数维杯国际大学生数学建模挑战赛D题洗衣房清洁计算解题全过程论文及程序

2023年数维杯国际大学生数学建模挑战赛 D题 洗衣房清洁计算 原题再现&#xff1a; 洗衣房清洁是人们每天都要做的事情。洗衣粉的去污作用来源于一些表面活性剂。它们可以增加水的渗透性&#xff0c;并利用分子间静电排斥机制去除污垢颗粒。由于表面活性剂分子的存在&#xff…

Ubuntu 20/22 安装 Jenkins

1. 使用 apt 命令安装 Java Jenkins 作为一个 Java 应用程序&#xff0c;要求 Java 8 及更高版本&#xff0c;检查系统上是否安装了 Java。 sudo apt install -y openjdk-17-jre-headless安装完成后&#xff0c;再次验证 Java 是否已安装 java --version2. 通过官方存储库安…

15:00面试,15:08出来,面试问的有点变态。。。。

&#x1f345; 视频学习&#xff1a;文末有免费的配套视频可观看 &#x1f345; 点击文末小卡片&#xff0c;免费获取软件测试全套资料&#xff0c;资料在手&#xff0c;涨薪更快 从小厂出来&#xff0c;没想到在另一家公司又寄了。 到这家公司开始上班&#xff0c;加班是每天…

第10章 数据聚合与分组运算

以下内容参考自https://github.com/iamseancheney/python_for_data_analysis_2nd_chinese_version/blob/master/%E7%AC%AC05%E7%AB%A0%20pandas%E5%85%A5%E9%97%A8.md 《利用Python进行数据分析第2版》 用以学习和记录。 对数据集进行分组并对各组应用一个函数&#xff08;无论…

Dubbo生态之dubbo功能

1.Dubbo生态功能的思考 dubbo具有哪些功能呢&#xff1f;我们要根据dubbo的架构和本质是用来干什么的来思考? 首先对于分布式微服务&#xff0c;假设我们有两个服务A和B&#xff0c;并且都是集群部署的。那么按照我们正常的流程应该是启动两个微服务项目&#xff08;启动时应该…

vscode添加代办相关插件,提高开发效率

这里写目录标题 前言插件添加添加TODO Highlight安装TODO Highlight在项目中自定义需要高亮显示的关键字 TODO Tree安装TODO Tree插件 单行注释快捷键 前言 在前端开发中&#xff0c;我们经常会遇到一些未完成、有问题或需要修复的部分&#xff0c;但又暂时未完成或未确定如何处…

C++初阶学习第十弹——探索STL奥秘(五)——深入讲解vector的迭代器失效问题

vector&#xff08;上&#xff09;&#xff1a;C初阶学习第八弹——探索STL奥秘&#xff08;三&#xff09;——深入刨析vector的使用-CSDN博客 vector&#xff08;中&#xff09;&#xff1a;C初阶学习第九弹——探索STL奥秘&#xff08;四&#xff09;——vector的深层挖掘和…

MYSQL 集群

1.集群目的:负载均衡 解决高并发 高可用HA 服务可用性 远程灾备 数据有效性 类型:M M-S M-S-S M-M M-M-S-S 原理:在主库把数据更改(DDL DML DCL&#xff09;记录到二进制日志中。 备库I/O线程将主库上的日志复制到自己的中继日志中。 备库SQL线程读取中继日志…

Mongodb介绍及springboot集成增删改查

文章目录 1. MongoDB相关概念1.1 业务应用场景1.2 MongoDB简介1.3 体系结构1.4 数据模型1.5 MongoDB的特点 2. docker安装mongodb3. springboot集成3.1 文件结构3.2 增删改查3.2.1 增加insert3.2.2 保存save3.2.3 更新update3.2.4 查询3.2.5 删除 1. MongoDB相关概念 1.1 业务…

【学习笔记】Windows GDI绘图(五)图形路径GraphicsPath详解(上)

文章目录 图形路径GraphicsPath填充模式FillMode构造函数GraphicsPath()GraphicsPath(FillMode)GraphicsPath(Point[],Byte[])和GraphicsPath(PointF[], Byte[])GraphicsPath(Point[], Byte[], FillMode)和GraphicsPath(PointF[], Byte[], FillMode)PathPointType 属性FillMode…

jsp连接数据库

1.打开命令框进入数据库 打开eclipse创建需要连接的项目 粘贴驱动程序 查看驱动器 使用sql的包 int代表个 conlm代表列名 <%page import"java.sql.ResultSet"%> <%page import"java.sql.Statement"%> <%page import"java.sql.Connect…

关于如何创建一个可配置的 SpringBoot Web 项目的全局异常处理

前情概要 这个问题其实困扰了我一周时间&#xff0c;一周都在 Google 上旅游&#xff0c;我要如何动态的设置 RestControllerAdvice 里面的 basePackages 以及 baseClasses 的值呢&#xff1f;经过一周的时间寻求无果之后打算决定放弃的我终于找到了一些关键的线索。 当然在此…

html5 笔记01

01 表单类型和属性 input的type属性 单行文本框: typetext 电子邮箱 : typeemail 地址路径 : type url 定义用于输入数字的字段: typenumber 手机号码: typetel 搜索框 : typesearch 定义颜色选择器 : typecolor 滑块控件 : typerange 定义日期 :typedate 定义输入时间的控件…

CR80清洁卡都能用在什么地方?

CR80清洁卡&#xff08;也被称为ISO 7810 ID-1清洁卡&#xff09;的规格确实使其在各种需要读取磁条或接触式智能卡的设备中都有广泛的用途。这些设备包括但不限于&#xff1a; ATM自动终端机&#xff1a;当ATM机的磁条读卡器出现故障或读卡不灵敏时&#xff0c;可以使用CR80清…

第三期【数据库主题文档上传激励活动】已开启!快来上传文档赢奖励

2023年9月、11月&#xff0c;墨天轮社区相继举办了第一期与第二期【数据库主题文档上传激励活动】&#xff0c;众多用户积极参与、上传了大量优质的数据库主题干货文档&#xff0c;在记录经验的同时也为其他从业者带来了参考帮助&#xff0c;这正实现了“乐知乐享、共同成长”的…

以及Spring中为什么会出现IOC容器?@Autowired和@Resource注解?

以及Spring中为什么会出现IOC容器&#xff1f;Autowired和Resource注解&#xff1f; IOC容器发展史 没有IOC容器之前 首先说一下在Spring之前&#xff0c;我们的程序里面是没有IOC容器的&#xff0c;这个时候我们如果想要得到一个事先已经定义的对象该怎么得到呢&#xff1f;…

STM32自己从零开始实操02:输入部分原理图

一、触摸按键 1.1指路 项目需求&#xff1a; 4个触摸按键&#xff0c;主控芯片 TTP224N-BSBN&#xff08;嘉立创&#xff0c;封装 TSSOP-16&#xff09;&#xff0c;接入到 STM32 的 PE0&#xff0c;PE1&#xff0c;PE2&#xff0c;PE3。 1.2走路 1.2.1数据手册重要信息提…

AI--构建检索增强生成 (RAG) 应用程序

LLM 所实现的最强大的应用之一是复杂的问答 (Q&A) 聊天机器人。这些应用程序可以回答有关特定源信息的问题。这些应用程序使用一种称为检索增强生成 (RAG) 的技术。 典型的 RAG 应用程序有两个主要组件 索引&#xff1a;从源中提取数据并对其进行索引的管道。这通常在线下…

CTFshow之文件上传web入门151关-161关解密。包教包会!!!!

这段时间一直在搞文件上传相关的知识&#xff0c;正好把ctf的题目做做写写给自字做个总结&#xff01; 不过有一个确定就是所有的测试全部是黑盒测试&#xff0c;无法从代码层面和大家解释&#xff0c;我找个时间把upload-labs靶场做一做给大家讲讲白盒的代码审计 一、实验准…

保研笔试复习——nju

文章目录 一、单选计算机网络计算机组成原理数字逻辑电路数据结构操作系统微机系统 多选题计算机网络计算机系统结构操作系统 免责声明&#xff1a;题目源自于网络&#xff0c;侵删。 就在今天2024-5-18&#xff0c;考的题下面的只有一道AVL的原题&#xff0c;其他都不是原题&a…