每日算法220522分区快速排序的从0到1
Posted 如何在5年薪百万
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了每日算法220522分区快速排序的从0到1相关的知识,希望对你有一定的参考价值。
今日题目
快速排序
通过选择数组的最右侧数作为分隔符,将数组分割成小于区域,等于区域,大于区域,周而复始,最终将数组排序。
今日心得
- 数组相关的算法,一旦出现大量的systemcopy就说明不是最优解,没有充分利用数组空间。
- 递归虽然理解很难,但是理解了解答就会很简单。只需要关注构建最小算法模型和边界条件。反而,使用非递归法的边界十分困难,非常容易出错。
- 如果能画出纸上的过程,代码就实现了一半。否则,代码会卡在边界条件处理上,绕不出。
算法编码
package sort;
/**
* @ClassName QuickSort
* @Description 快速排序
* <p>数组题一旦有太多copy就说明不是最优解,没有充分利用空间</p>
* @Author kouryoushine
* @Date 2022/5/22 10:20
* @Version 1.0
*/
public class QuickSort
public static void main(String[] args)
int[] arr = 1, 3, 7, 5, 4, 3, 9, 8, 3, 7, 2, 3, 5, 7;
quickSort(arr);
for (int a = 0; a < arr.length; a++)
System.out.println(arr[a]);
//用arr的最右数做区分,<=Rnum的放在左边,>Rnum的放在右边
public static void splitByRnum(int[] arr)
if (arr == null || arr.length == 0)
return;
int N = arr.length;
int lessArea = -1;
int index = 0;
;
int rNum = arr[N - 1];
while (index < N) //顺序遍历数组中每一个数
if (arr[index] <= rNum) //当前数比最右数小,则交换位置。最小区域又阔,下标右移。
swap(arr, lessArea + 1, index);
lessArea++;
index++;
else //当前数比最右大,则跳过,下标右移
index++;
/**
* 根据数组最右的值,将数据拆分成三个区域
* 小区域:less=-1
* 大区域:more=N-1
* 等于区域: [less+1:more-1]
* <p>
* 实现逻辑:
* index沿array遍历
* 见代码注释
*
* @param arr
*/
public static void splitNumByRnumIntoThreeAre(int arr[])
int N = arr.length;
int less = -1; //小区域有边界
int more = N - 1; //大区域左边界
int rNum = arr[N - 1];
int index = 0; //下标
while (index < more)
if (arr[index] < rNum)
swap(arr, less + 1, index);//小区域下一个数和当前值交换,下标和小区域右移
index++;
less++;
else if (arr[index] > rNum) //大区域前一个值和当前值交换,大区域左移。index不变
swap(arr, more - 1, index);
more--;
//index不变
else //跳过
index++;
//index=more时
swap(arr, index, N - 1);
/**
* 分区快排,将上面能力进一步抽象为L...R范围内的排序,过程一样。
*
* @return ==区域的左右边界
*/
public static int[] partiion(int[] arr, int L, int R)
int lessR = L - 1;
int moreL = R;
int rNum = arr[R];
int index = L;
while (index < moreL)
if (arr[index] < rNum)
swap(arr, lessR + 1, index);//小区域下一个数和当前值交换,下标和小区域右移
index++;
lessR++;
else if (arr[index] > rNum) //大区域前一个值和当前值交换,大区域左移。index不变
swap(arr, moreL - 1, index);
moreL--;
//index不变
else //跳过
index++;
swap(arr, R, index);
return new int[]lessR + 1, moreL; //moreL而不是moreL-1画出内存就知道了
public static void quickSort(int arr[])
if (arr == null || arr.length < 2)
return;
process(arr, 0, arr.length - 1);
//递归函数
public static void process(int[] arr, int L, int R)
if (L >= R)
return;
int[] equal = partiion(arr, L, R);//拆分成三个区域
int L1 = L;
int R1 = equal[0] - 1;
int L2 = equal[1] + 1;
int R2 = R;
process(arr, L1, R1);
process(arr, L2, R2);
public static void swap(int arr[], int i, int j)
int tmp = arr[i];
arr[i] = arr[j];
arr[j] = tmp;
以上是关于每日算法220522分区快速排序的从0到1的主要内容,如果未能解决你的问题,请参考以下文章