看动画学算法之:排序-快速排序

简介: 快速排序也采用的是分而制之的思想。那么快速排序和归并排序的区别在什么地方呢? 归并排序是将所有的元素拆分成一个个排好序的数组,然后将这些数组再进行合并。 而快速排序虽然也是拆分,但是拆分之后的操作是从数组中选出一个中间节点,然后将数组分成两部分。 左边的部分小于中间节点,右边的部分大于中间节点。 然后再分别处理左边的数组合右边的数组。

简介

快速排序也采用的是分而制之的思想。那么快速排序和归并排序的区别在什么地方呢?

归并排序是将所有的元素拆分成一个个排好序的数组,然后将这些数组再进行合并。

而快速排序虽然也是拆分,但是拆分之后的操作是从数组中选出一个中间节点,然后将数组分成两部分。

左边的部分小于中间节点,右边的部分大于中间节点。

然后再分别处理左边的数组合右边的数组。

快速排序的例子

假如我们有一个数组:29,10,14,37,20,25,44,15,怎么对它进行快速排序呢?

先看一个动画:

我们再分析一下快速排序的步骤。

我们选择的是最左边的元素29作为中间点元素,然后将数组分成三部分:[0, 14, 15, 20, 25],[29],[44, 37]。

中间节点29已经排好序了,不需要处理。

接下来我们再对左右分别进行快速排序。最后就得到了一个所有元素都排序的数组。

快速排序的java代码实现

我们先来看最核心的部分partition,如何将数组以中间节点为界,分成左右两部分呢?

我们的最终结果,是要将array分割成为三部分。

首先我们选择最左侧的元素作为中间节点的值。然后遍历数组中的其他元素。

假如m=middleIndex,k=要遍历的元素index

考虑两种情况,第一种情况是数组中的元素比中间节点的值要大。

这种情况下,m不需要移动,k+1继续遍历即可。

第二种情况下,数组中的元素比中间节点的值要小。

因为m左边的元素都要比中间节点的值要小,所以这种情况下m需要+1,即右移一位。

现在m+1位置的元素要么还没有进行比较,要么就是比中间节点的值要大,我们可以巧妙的将m+1位置的元素和k位置的元素互换位置,这样仍然能够保证m左侧的元素要比中间节点的值要小。

将上面的分析总结成java代码如下:

 private int partition(int[] array, int i, int j) {//选择最左侧的元素作为中心点,middleValue就是中心点的值int middleValue = array[i];int middleIndex = i;//从i+1遍历整个数组for (int k = i+1; k <= j; k++) {//如果数组元素小于middleValue,表示middleIndex需要右移一位//右移之后,我们需要将小于middleValue的array[k]移动到middleIndex的左边,// 最简单的办法就是交换k和middleIndex的值if (array[k] < middleValue) {middleIndex++;//交换数组的两个元素swap(array, k , middleIndex);} //如果数组元素大于等于middleValue,则继续向后遍历,middleIndex值不变}// 最后将中心点放入middleIndex位置swap(array, i, middleIndex);return middleIndex;}

最后我们需要将最左侧的元素和中间节点应该在的index的元素互换下位置,这样就将中间节点移动到了中间位置,并返回中间位置。

再来看下divide的代码:

    public void doQuickSort(int[] array, int low, int high) {//递归的结束条件if (low < high) {//找出中心节点的值int middleIndex = partition(array, low, high);//数组分成了三部分:// a[low..high] ~> a[low..m–1], pivot, a[m+1..high]//递归遍历左侧部分doQuickSort(array, low, middleIndex-1);// a[m] 是中心节点,已经排好序了,不需要继续遍历//递归遍历右侧部分doQuickSort(array, middleIndex+1, high);log.info("QuickSort之后的数组:{}",array);}}

divide的代码就很简单了,找到中间节点的位置之后,我们再分别遍历数组的左右两边即可。最后得到排好序的数组。

随机快速排序的java实现

上面的例子中,我们的中间节点的选择是数组的最左元素,为了保证排序的效率,我们可以从数组中随机选择一个元素来作为中间节点。

 private int partition(int[] array, int i, int j) {//随机选择一个元素作为中心点,middleValue就是中心点的值int randomIndex=i+new Random().nextInt(j-i);log.info("randomIndex:{}",randomIndex);//首先将randomIndex的值和i互换位置,就可以复用QuickSort的逻辑swap(array, i , randomIndex);int middleValue = array[i];int middleIndex = i;//从i遍历整个数组for (int k = i+1; k <= j; k++) {//如果数组元素小于middleValue,表示middleIndex需要右移一位//右移之后,我们需要将小于middleValue的array[k]移动到middleIndex的左边,// 最简单的办法就是交换k和middleIndex的值if (array[k] < middleValue) {middleIndex++;//交换数组的两个元素swap(array, k , middleIndex);} //如果数组元素大于等于middleValue,则继续向后遍历,middleIndex值不变}// 最后将中心点放入middleIndex位置swap(array, i, middleIndex);return middleIndex;}

上面的代码,我们在分区的时候,先选择出一个随机的节点,然后将这个随机的节点和最左侧的元素交换位置,后面的代码就可以重用上面的QuickSort的代码逻辑了。

快速排序的时间复杂度

从上面的分析我们可以看出,每次分区的时间复杂度应该是O(N),而divide又近似二分法,所以总的时间复杂度是O(N logN)。

 

 

原文链接
本文为阿里云原创内容,未经允许不得转载。

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

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

相关文章

思考、创新、坚持——阿里做了七年前端,我的成长经验分享

在成长的未知道路上&#xff0c;我们总会遇到各种各样的问题&#xff0c;但是&#xff0c;所有的迷茫与逆境都能够帮助我们成长&#xff0c;我们要抓住每一个机会让自己进步&#xff0c;而不是徘徊不前。 淘系前端开发同学——林晚&#xff0c;今天就来和大家分享他这七年的成长…

存储进阶:怎么才能保证 IO 数据的安全?

来源 | 奇伢云存储头图 | 下载于视觉中国写成功了数据就安全了吗&#xff1f;思考一个问题&#xff1a;写数据做到什么程度才叫安全了&#xff1f;就是&#xff1a;用户发过来一个写 IO 请求&#xff0c;只要你给他回复了 “写成功了”&#xff0c;那么无论机器发生掉电&#x…

设计稿生成代码与 Serverless 的前世今生与未来!

简介&#xff1a; 云栖大会云上 Hello World 活动火热进行中&#xff01;每位参与者都可收获一份阿里云出品的全球唯一序列号纪念证书&#xff01; 一场脑洞实验 云栖大会云上 Hello World 活动火热进行中&#xff01;每位参与者都可收获一份阿里云出品的全球唯一序列号纪念证…

ARMS在APM工具选型中的实践

简介&#xff1a; 当前的系统在数字化转型需求以及互联网架构实施的影响下&#xff0c;越来越普遍地使用了微服务架构&#xff0c;我们在享受微服务带来的好处&#xff08;开发效率高&#xff0c; 独立部署&#xff0c; 水平扩展&#xff0c; 故障与资源隔离等等&#xff09;外…

无人机、IoT 设备都有漏洞?专访以色列老牌安全公司 Check Point|拟合

从无序中寻找踪迹&#xff0c;从眼前事探索未来。 2021 年正值黄金十年新开端&#xff0c;CSDN 以中立技术社区专业、客观的角度&#xff0c;深度探讨中国前沿 IT 技术演进&#xff0c;推出年度重磅企划栏目——「拟合」&#xff0c;通过对话企业技术高管大咖&#xff0c;跟踪报…

从零入门 Serverless | 函数计算的可观测性

简介&#xff1a; 本文主要分为三个部分&#xff1a;概述中介绍可观测性的基本概念&#xff0c;主要包括 Logging、Metrics、Tracing 三个方面&#xff1b;然后详细介绍函数计算上的 Logging、Metrics、Tracing&#xff1b;最后以几个常见场景为例&#xff0c;介绍在函数计算中…

宜家:打造新零售时代的智能客户身份管理系统

简介&#xff1a; 宜家选择了阿里云应用身份服务&#xff08;IDaaS&#xff09;来为其提供一个包括统一认证、统一账户管理的CIAM解决方案&#xff0c;为所有前端提供统一的安全、可扩展和可靠的身份认证服务&#xff0c;包括灵活的认证配置、单点登录、多因素认证、社交平台登…

生意参谋牵手Quick BI 让数据再次驱动店铺经营

刚刚过去的一周&#xff0c;超两百家店铺体验了阿里巴巴官方全渠道、全链路、一站式数据平台生意参谋推出的全新功能&#xff0c;自助分析。 作为生意参谋联合Quick BI的初次尝试&#xff0c; “自助分析”面向店铺提供自助分析解决方案&#xff0c;支持店铺个性化数据报表制作…

到底是谁发明了物联网?

来源 | 鲜枣课堂作者 | 小枣君头图 | 下载于视觉中国1965年的越南战场&#xff0c;美军正深陷战争泥潭。突然有一天&#xff0c;北越士兵在胡志明小道发现了一些奇怪的东西。这些东西看上去像树枝&#xff0c;但实际上由金属构成&#xff0c;里面包含一些神秘的电子元件。这些士…

八种经典排序算法总结

前言 算法和数据结构是一个程序员的内功&#xff0c;所以经常在一些笔试中都会要求手写一些简单的排序算法&#xff0c;以此考验面试者的编程水平。下面我就简单介绍八种常见的排序算法&#xff0c;一起学习一下。 一、冒泡排序 思路&#xff1a; 比较相邻的元素。如果第一…

docker onlyoffice7.1.1 word excel ppt在线编辑、在线预览_部署01

文章目录1. 创建onlyoffice容器2. 启动在线案例3. 开放防火墙4. 浏览器验证5. 上传文件测试6. 在线编辑7. 测试主页面1. 创建onlyoffice容器 下面命令作用&#xff1a;拉取镜像、映射宿主机端口和docker内部端口、创建宿主机和docker容器挂载目录、拉取指定版本的onlyoffice/d…

漫画 | 程 序 员 脱 单 指 南

本文纯属娱乐&#xff0c;切勿模仿&#xff0c;模仿后果难以评估&#xff0c;务必小心再小心&#xff0c;谢谢&#xff01;

基于JindoFS+OSS构建高效数据湖

为什么要构建数据湖 大数据时代早期&#xff0c;Apache HDFS 是构建具有海量存储能力数据仓库的首选方案。随着云计算、大数据、AI 等技术的发展&#xff0c;所有云厂商都在不断完善自家的对象存储&#xff0c;来更好地适配 Apache Hadoop/Spark 大数据以及各种 AI 生态。由于…

docker onlyoffice7.1.1 word excel ppt在线编辑、在线预览_添加中文字体和中文字号_02

文章目录一、 onlyoffice添加中文字体1. 下载字体2. 上传字体3. 删除原版自带字体4. 字体复制5. 安装字体6. 重启容器7. 清除缓存8. 效果验证二、 onlyoffice添加中文中文字号2.1. 拷贝配置文件2.2. 编辑配置2.3. 上传配置2.4. 配置覆盖2.5. 重启容器2.6. 效果验证一、 onlyoff…

重磅报告 | 《中国企业2020:人工智能应用实践与趋势》

文章导读 AI设计师“鹿班”每秒可设计海报8000张&#xff0c;赋能30万商家备战“双十一”&#xff1b;光伏电池生产商天合光能运用人工智能算法将A品率提升7%&#xff0c;创造利润数千万&#xff1b;AI帮助优酷分析舆情选出爆款影视剧IP&#xff0c;打造了10天播放量超过60亿的…

OnlyOffice 修改文件大小限制

文章目录1. 拷贝配置到宿主机2. 配置调整3. 配置覆盖4. 容器重启5. 启动案例测试6. 查看日志1. 拷贝配置到宿主机 docker cp 58f75f6ca6f7:/etc/onlyoffice/documentserver/default.json ./2. 配置调整 vim default.json默认下载大小"maxDownloadBytes": 104857600,…

启明星辰集团:文化筑底,战略引领信息安全之路

4月30日&#xff0c;“启明星辰集团年度业绩说明与战略发布会”在上海成功举办&#xff0c;启明星辰集团总裁严立、集团CFO张媛、集团董秘姜朋出席会议&#xff0c;为投资者、用户、媒体解读企业未来战略布局&#xff0c;就行业状况、生产经营、财务状况进行说明&#xff0c;探…

【数据湖加速篇】 —— 如何利用缓存加速服务来提升数据湖上机器学习训练速度

简介&#xff1a; JindoFS提供了一个计算侧的分布式缓存系统&#xff0c;可以有效利用计算集群上的本地存储资源&#xff08;磁盘或者内存&#xff09;缓存OSS上的热数据&#xff0c;从而减少对OSS上数据的反复拉取&#xff0c;消耗网络带宽。 背景介绍 近些年&#xff0c;机…

OnlyOffice 二次开发定制化部署

文章目录一、与前准备1. 功能点总览2. 上传中文字体3. 上传镜像包4. 创建目录5. 字体挂载6. 加载镜像二、与前准备2.1. 创建容器2.2. 浏览器验证2.3. 在线编辑一、与前准备 1. 功能点总览 功能兼容性说明并发20限制去除√并发数999中文字体√41种常用字体中文字号√文件下载大…

何为“边缘计算”?

来源 | 无敌码农责编 | 寇雪芹头图 | 下载于视觉中国在云原生除了K8S、微服务&#xff0c;还有...?中和大家聊了下关于云原生的话题&#xff0c;在云原生的概念中比较明确的一个特点就是云原生是基于云计算的。在这种模式下用户的计算请求会被发送到云端服务进行处理&#xff…