普通快排,最差情況下爲時間複雜度O(N^2)
隨機快排,最差情況下爲時間複雜度O(N*logN),最好空間複雜度O(logN),最差O(N)
原始快排:將數組最後一個變量假設爲X,小於等於X的放左邊,大於X的放右邊,然後再將拍好序的左邊和右邊分別再重複剛剛的動作
改進快排:將數組最後一個變量假設爲X,小於X的放左邊,等於X的放中間,大於X的放右邊,這樣的好處是中間排好序的X不用動
public static void quickSort(int[] arr) {
if (arr == null || arr.length < 2) {//空或長度小於2個,不用排序
return;
}
quickSort(arr, 0, arr.length - 1);
}
//隨機快排,隨機取一個數,讓它和數組的最後一位交換,然後按最後一位進行普通快排
public static void quickSort(int[] arr, int l, int r) {
if (l < r) {//排序結束條件
//swap(arr, l + (int) (Math.random() * (r - l + 1)), r);隨機快排
int[] p = partition(arr, l, r);//以數組最後一個作爲比較的數,小於放左邊,等於放中間,大於放右邊,和荷蘭國旗問題一樣,只不過多了遞歸
quickSort(arr, l, p[0] - 1);//遞歸左邊,不包括等於的數字
quickSort(arr, p[1] + 1, r);//遞歸右邊,不包括等於的數字
}
}
public static int[] partition(int[] arr, int l, int r) {
int less = l - 1;
int more = r;
while (l < more) {
if (arr[l] < arr[r]) {
swap(arr, ++less, l++);
} else if (arr[l] > arr[r]) {
swap(arr, --more, l);
} else {
l++;
}
}
swap(arr, more, r);//默認最後一個數不參與排序,等排完和大於區域的第一個數交換
return new int[] { less + 1, more };
}
public static void swap(int[] arr, int i, int j) {
int tmp = arr[i];
arr[i] = arr[j];
arr[j] = tmp;
}