快速排序

定义

基本思想:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分分别进行快速排序,整个排序过程可以递归进行,以达到整个数据变成有序序列

稳定性

不稳定

时间复杂度

O(N * logN)

代码

测试用例

int arr[] = {2,4,3,1,6,5};

原代码

    /*** 快速排序* @param arr* @param len*/public static void quickSort(int[] arr, int len){System.out.println("初始数据 " + Arrays.toString(arr) + "\n\n");quickSort(arr,0,len-1);}/*** 快速排序* @param arr* @param low* @param high*/public static void quickSort(int[] arr,int low,int high) {int mid;if (low<high){mid = partition(arr,low,high); // 进行分割操作并返回基准元素quickSort(arr,low,mid -1); // 右区间递归快速排序quickSort(arr,mid+1,high); // 左区间递归快速排序}}/*** 返回基准* @param arr* @param low* @param high* @return*/public static int partition(int[] arr,int low, int high){System.out.println("开始下标 "+ low);System.out.println("结束下标 "+ high);int i = low; // 待处理第一个下标int j = high; // 待处理最后一个下标// 分界值int pivot = arr[low];System.out.println("分界值 [" + pivot + "]");while (i<j){// 从右往左扫描  跳出循环:j==i 或 arr[j] <= arr[pivot]while (i<j && arr[j]>pivot){j--;}// arr[i] 和 arr[j] 交换后,i右移一位if (i<j){swap(arr,i,j);System.out.println("右侧遍历 本次交换结果"+ Arrays.toString(arr));i++;}// 从左往右扫描 跳出循环 i==j 或 arr[i]>pivotwhile (i<j && arr[i]<=pivot){i++;}// arr[i] 和 arr[j] 交换后,j左移一位if (i<j){swap(arr,i,j);System.out.println("左侧遍历 本次交换结果" + Arrays.toString(arr));j--;}}// 返回最终划分完成后基准匀速所在的位置 i==jSystem.out.println("新基准下标 " + i + "\n");return i;}

代码解释

第一次对整体进行遍历,以第一个作为基准,分为两部分
具体遍历过程:
j:先从右往左,找到小于等于基准的数之后,跳出循环
交换i j 所指向的元素,i++;此时arr[i]待判断
i:从左往右,找到大于基准的数之后,跳出循环
交换i j 所指向的值,j–;此时arr[j]待判断; arr[i]已判断
结束条件:i==j (本轮遍历结束)

每次遍历的基准都是arr[low];

运行结果

交换函数

    /*** 交换函数* @param arr* @param i* @param j*/public static void swap(int[] arr,int i ,int j){int temp = arr[j];arr[j] = arr[i];arr[i] = temp;}

扩展 应用

分类问题

题面
给定⼀个数组arr,和⼀个数num,请把⼩于等于num的数放在数组的左边,⼤于num的数放在数组的
右边。
思路
注:指定num不一定在数组中

指针p从-1位置开始,规划p左侧为⼩于num的数的区域,然后准备⼀个指针q指向下标0位置,如果q
指向元素⼩于等于num,则q指向元素与p+1指向元素交换,p、q往后移动;如果q指向元素⼤于
num,则q往后移动,直到q移出数组。
时间复杂度
O(N)

代码实现

/*** @Classname Classify* @Description 分类问题*/
public class Classify {public static void main(String[] args) {// 测试数据int arr[] = {2,1,1,1,4,8,1,6,5};partition(arr,3);}/*** 分类* @param arr* @param pivot 分界值* @return*/public static int partition(int[] arr,int pivot){System.out.println("分界值 [" + pivot + "]");System.out.println("初始数据 " + Arrays.toString(arr)+"\n");int i = -1; // 用于记录比pivot小的值的下标 -1表示不存在int j = 0; // 用于遍历for (;j<arr.length;j++){// 只要比pivot小就和arr[i]交换if (j<arr.length && arr[j]<=pivot){swap(arr,i+1,j);i++;System.out.println("第"+(i+1)+"次交换结果 " +Arrays.toString(arr));}}System.out.println("最终结果 " + Arrays.toString(arr)+"\n");// 以下代码用于打印结果System.out.println("前"+(i+1)+"个为小于等于"+pivot+"的元素");System.out.println(pivot+"之前:");System.out.print("[ ");for (int n =0;n<=i;n++){System.out.print(arr[n] + " ");}System.out.print("]");System.out.println("\n"+pivot+"之后:");System.out.print("[ ");for (int n =i+1;n<arr.length;n++){System.out.print(arr[n] + " ");}System.out.println("]");return i;}/*** 交换函数* @param arr* @param i* @param j*/public static void swap(int[] arr,int i ,int j){int temp = arr[j];arr[j] = arr[i];arr[i] = temp;}}

运行结果

荷兰国旗问题

题面
给定⼀个数组arr,和⼀个数num,请把⼩于num的数放在数组的左边,等于num的数放在数组的中
间,⼤于num的数放在数组的右边。
时间复杂度
O(N)
代码实现

/*** @Classname HollandFlag* @Description 荷兰国旗*/
public class HollandFlag {public static void main(String[] args) {// 测试数据int arr[] = {-1,-2,-3,2,1,1,1,4,8,1,6,5};partition(arr,arr.length,1);}/**** @param arr* @param len* @param pivot* @return*/public static int partition(int[] arr,int len,int pivot){System.out.println("分界值 [" + pivot + "]");System.out.println("初始数据 " + Arrays.toString(arr)+"\n");int less = -1; // 记录比pivot小的值的下标 -1 表示没有int more = len; // 记录比pivot大的值的下标 arr.length表示没有System.out.println("分界值 [" + pivot + "]");int i=0;while (i<len&&less<more){if (arr[i]<pivot){swap(arr,i++,++less);System.out.println("小于"+Arrays.toString(arr));}else if (arr[i]>pivot&&i<more){// 因为是从左向右遍历 // 所以交换过来的数据(arr[i],原arr[--more])并没有被判断,所以这里i不加一  // 且要保证more和i的大小关系swap(arr,i,--more);System.out.println("大于"+Arrays.toString(arr));}else {i++;}}System.out.println("最终结果 " + Arrays.toString(arr)+"\n");// 以下代码用于打印结果System.out.println("小于"+pivot);System.out.print("[ ");for (int n =0;n<=less;n++){System.out.print(arr[n] + " ");}System.out.print("]");System.out.println("\n等于"+pivot);System.out.print("[ ");for (int n =less+1;n<more;n++){System.out.print(arr[n] + " ");}System.out.print("]");System.out.println("\n大于"+pivot);System.out.print("[ ");for (int n =more;n<len;n++){System.out.print(arr[n] + " ");}System.out.print("]");return i;}/*** 交换函数* @param arr* @param i* @param j*/public static void swap(int[] arr,int i ,int j){int temp = arr[j];arr[j] = arr[i];arr[i] = temp;}
}

运行结果

【算法】排序_快速排序相关推荐

  1. 重点算法排序之快速排序、归并排序(上篇)

    文章目录 一.排序的概念及常见的排序算法 二.快速排序的思想及代码详解 2.1 快速排序的思想 2.2 挖坑法 2.2.1 挖坑法实现思想 2.2.2 挖坑法举例 2.2.3 挖坑法代码实现 2.3 ...

  2. java sort算法名称_快速排序算法(Quick Sort)(java)

    /** * 快速排序算法是基于分治策略的一种排序算法,下面是一个递归的快速排序. * @author liuy */ public class QuickSort { public static vo ...

  3. 9个元素换6次达到排序序列_(算法四)高级排序(快速排序)

    1.快速排序 快速排序是对冒泡排序的一种改进.它的基本思想是:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分数据分别进行快速 ...

  4. 排序中减治法算法伪代码_算法浅谈——分治算法与归并、快速排序(附代码和动图演示)...

    在之前的文章当中,我们通过海盗分金币问题详细讲解了递归方法. 我们可以认为在递归的过程当中,我们通过函数自己调用自己,将大问题转化成了小问题,因此简化了编码以及建模.今天这篇文章呢,就正式和大家聊一聊 ...

  5. java的 交换排序 快速排序算法_数据结构之排序算法Java实现(4)—— 交换类排序之快速排序算法...

    快速排序算法属于"交换类"的排序,它的效率主要跟数据分布是否对称有关. 升序排序: /** * 快速排序 * 升序排序 */ @Override public > void ...

  6. js数组按中文拼音排序_通俗易懂讲 Python 算法:快速排序

    原文:https://stackabuse.com/quicksort-in-python/ 作者:Marcus Sanatan 译者:老齐 欢迎在 bilibili  搜索 freeCodeCamp ...

  7. 【排序综合】直接插入排序,希尔排序,快速排序,堆排序,冒泡排序,简单选择排序的简介,实现和算法复杂度分析

    目录 1. 直接插入排序 1.1 直接插入排序简介 1. 什么是直接插入排序 2. 排序思想 1.2 排序实现 1. 排序代码 2. 复杂度分析: 3. 运行结果: 1.3 学习链接 2. 希尔排序( ...

  8. 使用qsort对不连续的内存数据排序_一点就懂的十大经典排序算法

    我是CSDN博主「雨夜※繁华」,这是我的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明. 原文链接:一点就懂的经典十大排序算法_大数据_LH is programmin ...

  9. java排序算法总结_排序算法总结及Java实现

    1. 整体介绍 分类 排序大的分类可以分为两种,内排序和外排序.在排序过程中,全部记录存放在内存,则称为内排序,如果排序过程中需要使用外存,则称为外排序.主要需要理解的都是内排序算法: 内排序可以分为 ...

  10. java sorted排序_【算法】排序算法之计数排序

    前几回,我们已经对冒泡排序.直接插入排序.希尔排序.选择排序.快速排序.归并排序.堆排序做了说明分析.本回,将对计数排序进行相关说明分析. 一.排序算法系列目录说明 冒泡排序(Bubble Sort) ...

最新文章

  1. list.add时报错:Exception in thread “main“ java.lang.UnsupportedOperationException
  2. Linux系统CentOS下mysql的安装日志
  3. TensorFlow Serving 尝尝鲜
  4. VS2017 Intelligense C++ 设置的几个重点
  5. wxWidgets:wxRibbonButtonBar类用法
  6. ORA-12516:TNS:listener could not find available handler with matching protocol stack
  7. 深入浅出 Java 8 Lambda 表达式
  8. python tkinter treeview 高亮_满满的成就感~如何用python让你的想法拥有可操作性?(一)...
  9. C++ 构造函数 与 析构函数
  10. 在JavaScript中解析查询字符串[重复]
  11. 力扣-图解算法数据结构
  12. 程序员记录每天工作日志软件_程序员日志记录简介
  13. 深入浅出MySQL全文 下载
  14. LPDDR4协议规范之 (四)命令和时序
  15. 朋友国企干了5年java,居然不知道Dubbo是做什么呢?我真信了!
  16. Python 第五篇 自制数字贺卡
  17. 智课雅思词汇---二十五、-ate
  18. amazon s3cmd 安装、批量下载
  19. iOS开发-代码分析工具之Infer
  20. calipso是什么意思_porridge是什么意思_porridge的翻译_音标_读音_用法_例句_爱词霸在线词典...

热门文章

  1. 容器操作系统再添丁,AWS开源Bottlerocket,类似RancherOS?
  2. ZStack实践汇 | 详解ZStack高级功能--裸金属服务部署实践
  3. 【优化算法】正弦余弦算法(SCA)【含Matlab源码 1308期】
  4. 【优化算法】麻雀搜索优化算法(SSA)【含Matlab源码 1288期】
  5. 【优化预测】基于matlab贝叶斯网络优化LSTM预测【含Matlab源码 1158期】
  6. 【图像增强】基于matlab同态增晰图像增强【含Matlab源码 962期】
  7. 【人脸识别】基于matlab ksvd字典学习人脸表情识别【含Matlab源码 460期】
  8. python复制csv数据_如何使用Python将CSV数据复制到现有xlsx文件
  9. pytorch使用模型预测_使用PyTorch从零开始对边界框进行预测
  10. xkcd目录_12条展示AI真相的XKCD片段