快速排序(详细讲解)
如今的面试里面,快速排序成了一项必须要掌握的技能,面试官考快排的概率非常大,不管是从思路上还是实践上,都基本必问.快速排序是一个既高效又不浪费空间的一种排序算法.下面来详细讲解一番快速排序:
假设我们现在对“6 1 2 7 9 3 4 5 10 8”这个10个数进行排序。首先在这个序列中随便找一个数作为基准数。选取第一个数6作为基准数。在这个序列中,将所有比基准数大的数放在6的右边,比基准数小的数放在6的左边,类似下面这种排列:
3 1 2 5 4 6 9 7 10 8
在初始状态下,数字6在序列的第1位。我们的目标是将6挪到序列中间的某个位置,假设这个位置是k。现在就需要寻找这个k,并且以第k位为分界点,左边的数都小于等于6,右边的数都大于等于6。
快速排序
方法其实很简单:分别从初始序列“6 1 2 7 9 3 4 5 10 8”两端开始“探测”。先从右往左找一个小于6的数,再从左往右找一个大于6的数,然后交换他们。这里可以用两个变量i和j,分别指向序列最左边和最右边。我们为这两个变量起个好听的名字“哨兵i”和“哨兵j”。刚开始的时候让哨兵i指向序列的最左边(即i=1),指向数字6。让哨兵j指向序列的最右边(即=10),指向数字。
首先哨兵j开始出动。因为此处设置的基准数是最左边的数,所以需要让哨兵j先出动,这一点非常重要(请自己想一想为什么)。哨兵j一步一步地向左挪动(即j–),直到找到一个小于6的数停下来。接下来哨兵i再一步一步向右挪动(即i++),直到找到一个数大于6的数停下来。最后哨兵j停在了数字5面前,哨兵i停在了数字7面前。
现在交换哨兵i和哨兵j所指向的元素的值。交换之后的序列如下:6 1 2 5 9 3 4 7 10 8
到此,第一次交换结束。接下来开始哨兵j继续向左挪动(再友情提醒,每次必须是哨兵j先出发)。他发现了4(比基准数6要小,满足要求)之后停了下来。哨兵i也继续向右挪动的,他发现了9(比基准数6要大,满足要求)之后停了下来。此时再次进行交换,交换之后的序列如下:
6 1 2 5 4 3 9 7 10 8
第二次交换结束,“探测”继续。哨兵j继续向左挪动,他发现了3(比基准数6要小,满足要求)之后又停了下来。哨兵i继续向右移动,糟啦!此时哨兵i和哨兵j相遇了,哨兵i和哨兵j都走到3面前。说明此时“探测”结束。我们将基准数6和3进行交换。交换之后的序列如下:
3 1 2 5 4 6 9 7 10 8
到此第一轮“探测”真正结束。此时以基准数6为分界点,6左边的数都小于等于6,6右边的数都大于等于6。回顾一下刚才的过程,其实哨兵j的使命就是要找小于基准数的数,而哨兵i的使命就是要找大于基准数的数,直到i和j碰头为止。
OK,解释完毕。现在基准数6已经归位,它正好处在序列的第6位。此时我们已经将原来的序列,以6为分界点拆分成了两个序列,左边的序列是“3 1 2 5 4”,右边的序列是“9 7 10 8”。接下来还需要分别处理这两个序列。因为6左边和右边的序列目前都还是很混乱的。不过不要紧,我们已经掌握了方法,接下来只要模拟刚才的方法分别处理6左边和右边的序列即可。现在先来处理6左边的序列现吧。
左边的序列是“3 1 2 5 4”。请将这个序列以3为基准数进行调整,使得3左边的数都小于等于3,3右边的数都大于等于3。好了开始动笔吧
如果你模拟的没有错,调整完毕之后的序列的顺序应该是:
2 1 3 5 4
OK,现在3已经归位。接下来需要处理3左边的序列“2 1”和右边的序列“5 4”。对序列“2 1”以2为基准数进行调整,处理完毕之后的序列为“1 2”,到此2已经归位。序列“1”只有一个数,也不需要进行任何处理。至此我们对序列“2 1”已全部处理完毕,得到序列是“1 2”。序列“5 4”的处理也仿照此方法,最后得到的序列如下:
1 2 3 4 5 6 9 7 10 8
对于序列“9 7 10 8”也模拟刚才的过程,直到不可拆分出新的子序列为止。最终将会得到这样的序列,如下
1 2 3 4 5 6 7 8 9 10
到此,排序完全结束。细心的同学可能已经发现,快速排序的每一轮处理其实就是将这一轮的基准数归位,直到所有的数都归位为止,排序就结束了。下面上个霸气的图来描述下整个算法的处理过程。
import java.util.Arrays;public class QuickSort {public static void main(String[] args) {int[] nums={11,24,5,32,50,34,54,76};System.out.println("快速排序前:"+ Arrays.toString(nums));quickSort(nums,0,nums.length-1);System.out.println("快速排序后:"+ Arrays.toString(nums));}public static void quickSort(int[] nums, int start, int end){if(start>end) return;int i,j,base;i=start;j=end;base=nums[start];while (i<j){while (i<j && nums[j]>=base) j--;while (i<j && nums[i]<=base) i++;if(i<j){swap(nums,i,j);}}swap(nums,start,i);quickSort(nums,start,j-1);quickSort(nums,j+1,end);}public static void swap(int[] nums,int left,int right){int temp=nums[left];nums[left]=nums[right];nums[right]=temp;}
}
快速排序(详细讲解)相关推荐
- 基础算法——快速排序详细讲解
一.快速排序算法描述 基本思想: 1.每一轮排序选择一个基准点(pivot)进行分区 1.让小于基准点的元素的进入一个分区,大于基准点的元素的进入另一个分区 2.当分区完成时,基准点元素的位置就是其最 ...
- 算法题Nuts and Bolts(螺母螺钉)快速排序详细讲解(含流程图)
1. 思路 首先选择螺丝中的一个元素作为pivot,用螺丝把螺母分区,每次分区得到三个结果, A1,完全匹配的一对 A2,比螺丝小的螺母 A3,比螺丝大的螺母 将1中的螺母取出,用它对螺丝进行分区,可 ...
- 排序算法的详解和分析对比(详细讲解)
目录 前言 一.排序的概念 二.排序的分类 三.常见排序算法的原理以及思想 1. 直接插入排序 1.1 直接插入排序的思想 1.2 直接插入排序代码实现 1.3 直接插入排序的详细过程 1.4 直接插 ...
- 排序算法-算法时间复杂度和空间复杂度概念 详细讲解
排序算法-算法时间复杂度和空间复杂度概念 详细讲解 排序算法的介绍 排序也称排序算法(Sort Algorithm),排序是将一组数据,依指定的顺序进行排列的过程. 排序的分类: 1)内部排序: 指将 ...
- 适合新手练手,用Python爬取OPGG里英雄联盟英雄胜率及选取率,详细讲解加注释(建议收藏练手)
今天来个简单的小项目,适合新手拿来练手,在OPGG上爬取英雄联盟里的法师,ADC,打野,辅助所有英雄的胜率及选取率,是不是感觉很高大上,但是却很简单,只要用三十多行代码就能实现,详细讲解每一行代码加注 ...
- Python的零基础超详细讲解(第十三天)-Python的类与对象
基础篇往期文章如下: Python的零基础超详细讲解(第一天)-Python简介以及下载 Python的零基础超详细讲解(第二天)-Python的基础语法1 Python的零基础超详细讲解(第三天)- ...
- Python的零基础超详细讲解(第十二天)-Python函数及使用
基础篇往期文章: Python的零基础超详细讲解(第一天)-Python简介以及下载_编程简单学的博客-CSDN博客 Python的零基础超详细讲解(第二天)-Python的基础语法1_编程简单学的博 ...
- Python的零基础超详细讲解(第七天)-Python的数据的应用
往期文章 Python的零基础超详细讲解(第一天)-Python简介以及下载_编程简单学的博客-CSDN博客 Python的零基础超详细讲解(第二天)-Python的基础语法1_编程简单学的博客-CS ...
- Python的零基础超详细讲解(第五天)-Python的运算符
往期文章 Python的零基础超详细讲解(第一天)-Python简介以及下载_编程简单学的博客-CSDN博客 Python的零基础超详细讲解(第二天)-Python的基础语法1_编程简单学的博客-CS ...
最新文章
- 思考:行业客户项目中的代理商(国外厂商)
- 话里话外:信息整合之障
- 选择or不选择苹果的理由
- crm开源系统 tp框架_八个开源的 Spring Boot 前后端分离项目,一定要收藏!
- spring 启动加载数据_12个很棒的Spring数据教程来启动您的数据项目
- 读书笔记:《时间投资法》之二
- JavaScript 数组和对象
- webpack的多文件打包问题
- Deepin Linux修改Grub引导
- 改动Xmodem/Zmodem上传下载路径
- 数据结构之二叉查找树
- 【渝粤教育】广东开放大学 操作系统原理与应用 形成性考核 (46)
- 软件需求分析教程阅读笔记二
- 网络编程与分层协议设计:基于linux平台实现,网络编程与分层协议设计基于Linux平台实现[按需印刷]...
- 俄罗斯方块_代码+解析
- [dp]HDOJ4960 	Another OCD Patient
- 量子计算机qled,量子点发光原理详解
- 关于Apple ID相关设置
- HSSFCellStyle相关属性报错
- 超低功耗LCD液晶显示驱动芯片(IC)-VKL128-稳定性好,超低工作电流,低休眠电流-技术开发资料
热门文章
- web爬虫学习(四)——手机APP爬取
- 跟着iMeta学做图|NMDS分析展示群落beta多样性
- oracle连接失败的原因总结
- 孟岩:想抓住EOS的机会,从这四个方向入手吧!
- Java之原子性-乐观锁与悲观锁
- 纽约州立大学水牛城分校计算机科学专业,美国布法罗大学(纽约州立大学水牛城分校)介绍/专业/申请条件/奖学金 | Hotcourses中国...
- 【PAC集成电机控制芯片】了解PAC集成电机控制芯片
- CNN(Convolutional Neural Network)
- ubuntu清除cuda缓存
- 字节跳动今日头条笔试题目经历2018