7.9快速排序
7.9.1快速排序法介绍:
快速排序(Quicksort)是对冒泡排序的一种改进。基本思想是:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分数据分别进行快速排序,整个排序过程可以递归进行,以此达到整个数据变成有序序列
7.9.2快速排序法示意图:
7.9.3快速排序法应用实例:
要求: 对 [-9,78,0,23,-567,70] 进行从小到大的排序,要求使用快速排序法。【测试8w和800w】
说明[验证分析]:
1)如果取消左右递归,结果是 -9 -567 0 23 78 70
2)如果取消右递归,结果是 -567 -9 0 23 78 70
3)如果取消左递归,结果是 -9 -567 0 23 70 78
4)代码实现
快速排序
import java.util.Arrays;/*** 快速排序*/
public class QuickSort {public static void main(String[] args) {int[] arr = {-9, 78, 0, 23, -567, 70};System.out.println("排序前:" + Arrays.toString(arr));quickSort(arr, 0, arr.length - 1);System.out.println("排序后:" + Arrays.toString(arr));}public static void quickSort(int[] arr, int left, int right) {int l = left;//左下标int r = right;//右下标//pivot中轴值int pivot = arr[(left + right) / 2];int temp = 0;//临时遍历,作为交换时使用//while循环的目的是,让比pivot值 小的,放到左边//比pivot值大的,放到右边while (l < r) {//在pivot的左边一直找,找到大于等于pivot值,才退出while (arr[l] < pivot) {l += 1;}//在pivot的右边一直找,找到小于等于pivot值,才退出while (arr[r] > pivot) {r -= 1;}//如果 l >= r ,说明pivot的左右两的值,已经按照左边全部是//小于等于pivot值,右边全部是大于等于pivot值if (l >= r) {break;}//交换temp = arr[l];arr[l] = arr[r];arr[r] = temp;//如果交换完后,发现这个arr[l] == pivot值,相等 r--, 前移if (arr[l] == pivot) {r -= 1;}//如果交换完后,发现这个arr[r] == pivot值,相等 l++, 后移if (arr[l] == pivot) {l += 1;}}//如果 l == r, 必须 l++, r--,否则会出现栈溢出if (l == r) {l += 1;r -= 1;}//向左递归if (left < r) {quickSort(arr, left, r);}//向右递归if (right > l) {quickSort(arr, l, right);}}
}
排序前:[-9, 78, 0, 23, -567, 70]
排序后:[-567, -9, 0, 23, 70, 78]
测试速度
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;/*** 快速排序*/
public class QuickSort {public static void main(String[] args) {//测试快速排序的速度, 给80000个数据 测试int arr[] = new int[80000];for (int i = 0, size = arr.length; i < size; i++) {arr[i] = (int) (Math.random() * 80000);//生成一个【0,80000)数}long startTime = System.currentTimeMillis();quickSort(arr, 0, arr.length - 1);long endTime = System.currentTimeMillis();SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");String start = dateFormat.format(new Date(startTime));String end = dateFormat.format(new Date(endTime));System.out.println("排序前时间:" + start);// 2023-08-20 15:11:38System.out.println("排序后时间:" + end);// 2023-08-20 15:11:38}public static void quickSort(int[] arr, int left, int right) {int l = left;//左下标int r = right;//右下标//pivot中轴值int pivot = arr[(left + right) / 2];int temp = 0;//临时遍历,作为交换时使用//while循环的目的是,让比pivot值 小的,放到左边//比pivot值大的,放到右边while (l < r) {//在pivot的左边一直找,找到大于等于pivot值,才退出while (arr[l] < pivot) {l += 1;}//在pivot的右边一直找,找到小于等于pivot值,才退出while (arr[r] > pivot) {r -= 1;}//如果 l >= r ,说明pivot的左右两的值,已经按照左边全部是//小于等于pivot值,右边全部是大于等于pivot值if (l >= r) {break;}//交换temp = arr[l];arr[l] = arr[r];arr[r] = temp;//如果交换完后,发现这个arr[l] == pivot值,相等 r--, 前移if (arr[l] == pivot) {r -= 1;}//如果交换完后,发现这个arr[r] == pivot值,相等 l++, 后移if (arr[l] == pivot) {l += 1;}}//如果 l == r, 必须 l++, r--,否则会出现栈溢出if (l == r) {l += 1;r -= 1;}//向左递归if (left < r) {quickSort(arr, left, r);}//向右递归if (right > l) {quickSort(arr, l, right);}}
}