快速排序算法备考

image.png

image.png

快排模板

快速排序(快排) (C语言实现)_c语言快速排序_Brant_zero2022的博客-CSDN博客
快排使用递归来实现
关键思想:划分


//划分
int partion(int A[],int L,int R){int mid=A[L];while(L<R){//每一次划分:左边元素<枢轴元素<右边元素//R往前找,直到找到一个比mid小的元素,然后把A[R]放在A[L]的位置while(A[R]>=mid && L<R){R--;}A[L]=A[R];while(A[R]<=mid && L<R){L++;}A[R]=A[L];}//存放枢轴元素A[L]=mid;return L;
}//快排
void quickSort(int A[],int L,int R){if(L>=R) return;//递归终止int M=partion(A,L,R);//返回中轴元素的下标//对中轴元素两边分别排序quickSort(A,L,M-1);quickSort(A,M+1,R);}

快排的划分思想

image.png

快排划分思想的算法题

使用划分函数找到数组中第k小的元素

  • 数组中第k小的元素,说明这个元素的左边有k-1个元素比它小,利用快排的划分思想,我们只需要让划分函数返回k-1,就可以找到第k小元素。
  • 如果第一次划分后,返回下标为k-1,那么,我们就找到了这个元素
  • 如果返回的下标>k-1,说明接下来要在[L,M-1]进行划分
  • 如果返回的下标<k-1,说明接下来要在右边进行划分

int partion(int A[],int L,int R){int mid=A[L];while(L<R){	while(A[R]>=mid && L<R) R--;A[L]=A[R];while(A[L]<=mid && L<R) L++A[R]=A[L];}A[L]=mid;}
//非递归实现
int min_k(int A[],int n,int k){int L=0,R=n-1;int M=0;while(1){M=partion(A,L,R);if(M==k-1)  break;//说明找到了else if(M<k-1){//在右边进行划分L=M+1;}else{//在左边进行划分R=M-1;}}return A[K-1]}//递归实现
int min_k(int A[],int L,int R){int M=partion(A,L,R);if(M==k-1)  return A[M];//说明找到了else if(M<k-1){//在右边进行划分min_k(A,M+1,R);}else{min_k(A,L,M-1);}}

分析非递归的复杂度
image.png
image.png

王道课后习题:在数组中找到第k小的元素

image.png
第k小,说明左边有k-1个元素比它小,利用快排的划分思想,只要返回下标为k即可

利用划分思想
//返回划分后的中轴元素的下标
int partion(int L,int left,int right){int mid=L[left];while(left<right){while(L[right]>=mid && left<right) right--;L[left]=L[right];while(L[left]<=mid && left<=right) left++;L[right]=L[left];}L[left]=mid;return left;}int min_k(int L[],int n,int k){int left=1,right=n,M=0;while(1){M=partion(L,left,right);if(M==k) break;else if(M<k)  left=M+1;//要在右边进行划分else right=M-1;//左边划分}return L[k];}

快排算法题实战应用

2011年42题

image.png

方法一双指针(我自己第一遍就想到的思路)

  1. 使用双指针,i指向序列S1元素,j指向S2序列元素,cnt用来记录已经比较的次数。比较s1,s2所指元素大小,如果S1所指元素大,则j向后移动,然后cnt++,如果S2所指元素大,则i向后移动,cnt++,当cnt==L/2时,此时,s1,s2所指元素大的那个就是中位数
  2. 代码

int find(int s1[],int s2[],int n){int i=j=cnt=0;for(cnt=0;cnt<n/2;cnt++;){if(s1[i]<s2[j]){i++;}else{j++; } }//接下来比较s1,s2所指元素大小if(s1[i]>s2[j]){return s1[i];}else{return s2[j];}}

时间复杂度:o(n)
空间复杂度:o(1)

方法二利用快排解决问题

把两个数组合并成一个大数组,然后用快排,下标L/2的元素就是中位数
image.png


//快排划分
int partion(int a[].int L,int R){int mid=a[L];while(L<R){while(a[R]>=mid&& L<R) R--;a[L]=a[R];while(a[L]>=mid && L<R) L++;a[R]=a[L];a[L]=mid;return L;}
//快排void qSort(int a[],int L,int R){if(L<=R) return;int M=partion(a,L,R);qSort(a,L,M-1);qSort(a,M+1,R);}void find(int s1[],int s2[],int n){int a[2*n];int i,j=0;//合并成一个数组for( i=0;i<n;i++)c[j++]=s1[i];}for( i=n;i<2*n;j++){c[j++]=s2[i];}//排序qSort(a,0,2*n-1);return (0+2*n-1)/2;}

2013年41题

方法一利用哈希表(第一遍所想)

1.cnt数组记录元素大小0~n-1出现的次数,出现次数大于n/2的元素就是主元素
2.代码void mainElement(int a[],int n){int cnt[n]={0};//元素值为i就存放在cnt数组的下标为i的位置,并且cnt对应位置元素值+1for(int i=0;i<n;i++){cnt[a[i]]++;}//扫描cnt数组for(int i=0;i<n;i++){if(cnt[i]>n/2) court<<i<<endl;}court<<"不存在主元素"<<endl;}
3.时间复杂度:o(n)空间复杂度o(n)

方法二快排

主元素的元素数量超过数组长度的一半,如果数组有序,并且存在主元素,那么主元素一定在数组的中间位置
image.png

①无序--->有序  快排
②找n/2位置的元素
③从n/2往左、往右统计个数,然后判断存不存在

image.png

2018年41题

image.png
54

方法一哈希表

cnt数组用来记录元素i是否出现在数组中,cnt记录1n,如果元素i位于1n,则对应cnt数组相应位置+1


int fun(int a[],int n){int cnt[n+1];for(int i=0;i<n;i++){if(a[i]>=1 && a[i]<=n) {cnt[a[i]]++;}}//遍历cnt数组,如果cnt[i]==0,说明就是未出现的最小正整数for(int i=1;i<n;i++){if(cnt[i]==0) return i;}//说明1~n都存在return n+1;}时间复杂度  O(n)空间复杂度  O(n)

image.png

方法二快排

image.png

2016年43题(本质是把乱序数组排成有序)

image.png

方法一利用快排

思路:想办法让右边元素大,左边元素小,而且尽量要把数组尽量平分,想到快排的划分思想,为了满足上述条件,右半部分的元素不能比左边元素个数少。
左边:0~n/2-1
右边:n/2~n-1

  1. 把数组A排成递增有序数列,排序后集合A1为[0,n/2-1],集合A2为[n/2n-1]

    此时[S1-S2]最大,[n1-n2]最小
    2.代码

①无序数组拍成有序数组
②说明A1,A2所在区间范围//划分
int partion(int A[],int L,int R){int mid=A[L];while(L<R){//每一次划分:左边元素<枢轴元素<右边元素//R往前找,直到找到一个比mid小的元素,然后把A[R]放在A[L]的位置while(A[R]>=mid && L<R){R--;}A[L]=A[R];while(A[R]<=mid && L<R){L++;}A[R]=A[L];}//存放枢轴元素A[L]=mid;return L;
}//快排
void quickSort(int A[],int L,int R){if(L>=R) return;//递归终止int M=partion(A,0,n-1);//返回中轴元素的下标//对中轴元素两边分别排序quickSort(A,L,M-1);quickSort(A,M+1,R);}
  1. 时间复杂度

    空间复杂度

image.png

方法二利用划分的思想(最优解)

我们知道快排在进行一次划分后,该元素的左边元素都比它小,右边都比它大。我们这道题目本质是把元素大的放右边,元素小的放左边,并没有要求按照 递增进行排序。其实,我们只要找到数组中第n/2小的元素。只要这个元素的位置确定了,那么它左边元素都比它小,右边都比它大。

//划分
int partion(int A[],int L,int R){int mid=A[L];while(L<R){//每一次划分:左边元素<枢轴元素<右边元素//R往前找,直到找到一个比mid小的元素,然后把A[R]放在A[L]的位置while(A[R]>=mid && L<R){R--;}A[L]=A[R];while(A[R]<=mid && L<R){L++;}A[R]=A[L];}//存放枢轴元素A[L]=mid;return L;
}
//
void fun(int A[],int n){int M=0;int k=n/2;int L=0,R=n-1;while(1){M=partion(A,L,R);if(M==k-1) break;else if(M<k-1) L=M+1;else R=M-1}//跳出循环说明已经找到第n/2小的元素}

image.png

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

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

相关文章

IO系列(八) -浅析NIO工作原理

一、简介 现在使用 NIO 的场景越来越多&#xff0c;很多网上的技术框架或多或少的使用 NIO 技术&#xff0c;譬如 Tomcat、Jetty、Netty&#xff0c;学习和掌握 NIO 技术已经不是一个 Java 攻城狮的加分技能&#xff0c;而是一个必备技能。 那什么是 NIO 呢&#xff1f; NIO…

不拍视频,不直播怎么在视频号卖货赚钱?开一个它就好了!

大家好&#xff0c;我是电商糖果 视频号这两年看着抖音卖货的热度越来越高&#xff0c;也想挤进电商圈。 于是它模仿抖音推出了自己的电商平台——视频号小店。 只要商家入驻视频号小店&#xff0c;就可以在视频号售卖商品。 具体怎么操作呢&#xff0c;需要拍视频&#xf…

Redis实践—全国地址信息缓存

一、背景 在涉及全国地址的应用中&#xff0c;地址信息通常被频繁地查询和使用&#xff0c;例如电商平台、物流系统等。为了提高系统性能和减少对数据库的访问压力&#xff0c;可以使用缓存来存储常用的地址信息&#xff0c;其中 Redis 是一个非常流行的选择。 本次在一个企业入…

就业信息|基于SprinBoot+vue的就业信息管理系统(源码+数据库+文档)

就业信息管理系统 目录 基于SprinBootvue的就业信息管理系统 一、前言 二、系统设计 三、系统功能设计 1前台功能模块 2后台功能模块 4.2.1管理员功能 4.2.2学生功能 4.2.3企业功能 4.2.4导师功能 四、数据库设计 五、核心代码 六、论文参考 七、最新计算机毕设…

[力扣]——70.爬楼梯

题目描述&#xff1a; 假设你正在爬楼梯。需要 n 阶你才能到达楼顶。 每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢&#xff1f; 本题较为简单&#xff0c;主要用到递归思想 int fun(int n,int memo[]) {if(memo[n]!-1) //如果备忘录中已经有记录了…

学 Go 具体能干什么?

学习 Go (Golang) 后&#xff0c;你可以从事许多不同的工作和项目&#xff0c;Go 语言以其高性能、并发处理和简洁的语法而闻名&#xff0c;特别适合以下几个领域&#xff1a; 1. 后端开发 Go 在后端开发中非常流行&#xff0c;特别适合构建高性能的 Web 服务和 API。 Web 框…

安卓获取内部存储信息

目录 前言获取存储容量 前言 原生系统设置里的存储容量到底是怎么计算的&#xff0c;跟踪源码&#xff0c;涉及到VolumeInfo、StorageManagerVolumeProvider、PrivateStorageInfo、StorageStatsManager......等等&#xff0c;java上层没有办法使用简单的api获取到吗&#xff1f…

【全开源】分类记账小程序系统源码(ThinkPHP+FastAdmin+UniApp)

基于ThinkPHPFastAdminUniAppvk-uView-uiVue3.0开发的一款支持多人协作的记账本小程序&#xff0c;可用于家庭&#xff0c;团队&#xff0c;组织以及个人的日常收支情况记录&#xff0c;支持周月年度统计。 &#xff1a;智能管理您的财务生活 一、引言&#xff1a;财务智能化…

多线程编程(12)之HashMap1.8源码分析

之前已经分析过了一版1.7版本的HashMap&#xff0c;这里主要是来分析一下1.8HashMap源码。 一、HashMap数据结构 HashMap 是一个利用散列表&#xff08;哈希表&#xff09;原理来存储元素的集合&#xff0c;是根据Key value而直接进行访问的数 据结构。 在 JDK1.7 中&#xff…

Text Control 控件 中 Service Pack 3:MailMerge 支持 SVG 图像

图像的合并方式与报告模板中的合并字段相同。占位符在设计时添加&#xff0c;并与文件、数据库或内存中的数据合并。可以将图像对象添加到具有指定名称的模板中。数据列必须包含字节数组形式的二进制图像数据、System.Drawing.Image 类型的对象、文件名、十六进制或 Base64 编码…

产品经理-需求收集(二)

1. 什么是需求 指在一定的时期中&#xff0c;一定场景中&#xff0c;无论是心理上还是生理上的&#xff0c;用户有着某种“需要”&#xff0c;这种“需要”用户自己不一定知道的&#xff0c;有了这种“需要”后用户就有做某件事情的动机并促使达到其某种目的&#xff0c;这也就…

Python 开心消消乐

&#x1f49d;&#x1f49d;&#x1f49d;欢迎莅临我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐:「stormsha的主页」…

记一次绕过宝塔防火墙的BC站渗透

0x00 信息收集 由于主站存在云waf 一测就封 且初步测试不存在能用得上的洞 所以转战分站 希望能通过分站获得有价值的信息 这是一个查询代理帐号的站 url输入admin 自动跳转至后台 看这个参数 猜测可能是thinkCMF 0x01 getshell thinkcmf正好有一个RCE 可以尝试一下 ?afetc…

01.爬虫---初识网络爬虫

01.初识网络爬虫 1.什么是网络爬虫2.网络爬虫的类型3.网络爬虫的工作原理4.网络爬虫的应用场景5.网络爬虫的挑战与应对策略6.爬虫的合法性总结 1.什么是网络爬虫 网络爬虫&#xff0c;亦称网络蜘蛛或网络机器人&#xff0c;是一种能够自动地、系统地浏览和收集互联网上信息的程…

SpringValidation

一、概述&#xff1a; ​ JSR 303中提出了Bean Validation&#xff0c;表示JavaBean的校验&#xff0c;Hibernate Validation是其具体实现&#xff0c;并对其进行了一些扩展&#xff0c;添加了一些实用的自定义校验注解。 ​ Spring中集成了这些内容&#xff0c;你可以在Spri…

一文教你如何调用Ascend C算子

Ascend C是CANN针对算子开发场景推出的编程语言&#xff0c;原生支持C和C标准规范&#xff0c;兼具开发效率和运行性能。基于Ascend C编写的算子程序&#xff0c;通过编译器编译和运行时调度&#xff0c;运行在昇腾AI处理器上。使用Ascend C&#xff0c;开发者可以基于昇腾AI硬…

AC/DC电源模块:提供高质量的电力转换解决方案

BOSHIDA AC/DC电源模块&#xff1a;提供高质量的电力转换解决方案 AC/DC电源模块是一种电力转换器件&#xff0c;可以将交流电转换为直流电。它通常用于各种电子设备和系统中&#xff0c;提供高质量的电力转换解决方案。 AC/DC电源模块具有许多优点。首先&#xff0c;它能够提…

【学习笔记】计算机组成原理(七)

指令系统 文章目录 指令系统7.1 机器指令7.1.1 指令的一般格式7.1.2 指令字长 7.2 操作数类型和操作类型7.2.1 操作数类型7.2.2 数据在存储器中的存放方式7.2.3 操作类型 7.3 寻址方式7.3.1 指令寻址7.3.1.1 顺序寻址7.3.1.2 跳跃寻址 7.3.2 数据寻址7.3.2.1 立即寻址7.3.2.2 直…

探秘SpringBoot默认线程池:了解其运行原理与工作方式(@Async和ThreadPoolTaskExecutor)

文章目录 文章导图Spring封装的几种线程池SpringBoot默认线程池TaskExecutionAutoConfiguration&#xff08;SpringBoot 2.1后&#xff09;主要作用优势使用场景如果没有它 2.1版本以后如何查看参数方式一&#xff1a;通过Async注解--采用ThreadPoolTaskExecutordetermineAsync…

Samtec技术漫谈 | 电动自行车中的传感器和信号传输技术

【摘要/前言】 电动自行车&#xff0c;大家熟悉吗&#xff1f; 今天的话题似乎是可以唤起大家心底骑车的美好回忆&#xff0c;我们也曾骑车探索过大自然和社区&#xff0c;自行车也是我们曾经不可或缺的便捷交通工具。 怀旧思潮的影响&#xff0c;加持科技的进步&#xff0c…