快速排序是一个很经典的排序算法,,面试很喜欢问,十分重要,最近回顾了一下快排,用Java做以实现。
一,基本思想
快排,是基于分治策略的一种排序算法。(从小到大为例)
【1】选择一个基准
【2】分别从两头进行遍历,把大于基准的放在左边,小于基准的放在右边,最终把基准插入即可。
【3】分别对左右两块进行【1】【2】操作,,直至快中只有一个元素。
有点负责,简化一下:“找基准,分两块,递归。”
二,实现算法
快速排序实现算法如下:
private static void quickSort(int[] array) {
if (array != null) {
quickSort(array, 0, array.length - 1);
}
}
private static void quickSort(int[] array, int start, int end) {
if (start >= end || array == null) { //null校验
return;
}
int p = partition(array, start, end);//大数放左边,,小数放右边
quickSort(array, start, p - 1);//对左边递归排序
quickSort(array, p + 1, end);//对右边递归排序
}
**private static int partition(int[] array, int start, int end)**,,方法两种实现
【实现1】
private static int partition(int[] array, int start, int end) {
int first = array[start];//以第一个为基准
int i = start + 1, j = end;
while (i < j) {//i == j是不容易发生的,,除非j = end,,i = end
while (array[i] <= first && i < end) {//等于时也算小,大于end就越界了
i++;
}
while (array[j] > first && j > start) {//大于等于start,,是为了和
j--;
}
if (i < j) {//利用异或交换array[i]和array[j]
array[i] = array[i] ^ array[j];
array[j] = array[j] ^ array[i];
array[i] = array[i] ^ array[j];
}
}
if (j != start) {//结束时,array[j]是小于first,,所以需要把小于的和first互换
array[start] = array[start] ^ array[j];
array[j] = array[j] ^ array[start];
array[start] = array[start] ^ array[j];
}
return j;//返回基准位置
}
【实现2】
private static int partition(int[] array, int start, int end) {
int last = array[end];//以最后一个为基准
int i = start, j;
for (j = start; j <= end - 1; j++) {
if (array[j] <= last) {
if (i != j) {//交换时,array[i]是大于基准的,,array[j],小于基准
array[i] = array[i] ^ array[j];
array[j] = array[j] ^ array[i];
array[i] = array[i] ^ array[j];
}
i++;
}
}
if (i != end) {//如果分成两块,则需要把基准数换到第二块的首位。反之array[i],,即为end
array[i] = array[i] ^ array[end];
array[end] = array[end] ^ array[i];
array[i] = array[i] ^ array[end];
}
return i; //返回基准位置
}
三,测试完整代码
package ddchuxing;
import java.util.ArrayList;
import java.util.List;
/**
* Created by zsl on 2017/8/26.
*/
public class QuicSort {
public static void main(String[] args) {
int array[] = {13, 14, 13, 4, 5, 6, 7, 7, 10, -1, 15};
quickSort(array);
System.out.println("快排结果");
for (int i = 0; i < array.length; i++) {
System.out.print(array[i] + " ");
}
}
private static void quickSort(int[] array) {
if (array != null) {
quickSort(array, 0, array.length - 1);
}
}
private static void quickSort(int[] array, int start, int end) {
if (start >= end || array == null) { //null校验
return;
}
int p = partition(array, start, end);//大数放左边,,小数放右边
quickSort(array, start, p - 1);//对左边递归排序
quickSort(array, p + 1, end);//对右边递归排序
}
/**
* 方法一
*/
// private static int partition(int[] array, int start, int end) {
// int first = array[start];//以第一个为基准
// int i = start + 1, j = end;
// while (i < j) {//i == j是不容易发生的,,除非j = end,,i = end
// while (array[i] <= first && i < end) {//等于时也算小,大于end就越界了
// i++;
// }
// while (array[j] > first && j > start) {//大于等于start,,是为了和
// j--;
// }
// if (i < j) {//利用异或交换array[i]和array[j]
// array[i] = array[i] ^ array[j];
// array[j] = array[j] ^ array[i];
// array[i] = array[i] ^ array[j];
// }
// }
// if (j != start) {//结束时,array[j]是小于first,,所以需要把小于的和first互换
// array[start] = array[start] ^ array[j];
// array[j] = array[j] ^ array[start];
// array[start] = array[start] ^ array[j];
// }
// return j;//返回基准位置
// }
/**
* 方法二
*
* @param array
* @param start
* @param end
* @return
*/
private static int partition(int[] array, int start, int end) {
int last = array[end];//以最后一个为基准
int i = start, j;
for (j = start; j <= end - 1; j++) {
if (array[j] <= last) {
if (i != j) {//交换时,array[i]是大于基准的,,array[j],小于基准
array[i] = array[i] ^ array[j];
array[j] = array[j] ^ array[i];
array[i] = array[i] ^ array[j];
}
i++;
}
}
if (i != end) {//如果分成两块,则需要把基准数换到第二块的首位。反之array[i],,即为end
array[i] = array[i] ^ array[end];
array[end] = array[end] ^ array[i];
array[i] = array[i] ^ array[end];
}
return i; //返回基准位置
}
}