歸併排序使用的就是分治思想。如果要排序乙個陣列,我們先把陣列從中間分成前後兩部分,然後對前後兩部分分別排序,再將排好序的兩部分合併在一起,這樣整個陣列就都有序了。
歸併排序的時間複雜度任何情況下都是 o(nlogn),但是,歸併排序並沒有像快排那樣應用廣泛,這是因為它有乙個致命的「弱點」,那就是歸併排序不是原地排序演算法。
在任意時刻,cpu 只會有乙個函式在執行,也就只會有乙個臨時的記憶體空間在使用。臨時記憶體空間最大也不會超過 n 個資料的大小,所以空間複雜度是 o(n)。
快排是一種原地、不穩定的排序演算法。#include
using
namespace std;
void
merge
(int a,
int start,
int end)
for(
int k = start;k <= end;k++)}
void
mergesort
(int a,
int p,
int r)
intmain()
;mergesort
(num,0,
11);for
(int i =
0;i <
12;i++
)return0;
}
思想:如果要排序陣列中下標從 p 到 r 之間的一組資料,我們選擇 p 到 r 之間的任意乙個資料作為 pivot(分割槽點)。我們遍歷 p 到 r 之間的資料,將小於 pivot 的放到左邊,將大於 pivot 的放到右邊,將 pivot 放到中間。
經過這一步驟之後,陣列 p 到 r 之間的資料就被分成了三個部分,前面 p 到 q-1 之間都是小於 pivot 的,中間是 pivot,後面的 q+1 到 r 之間是大於 pivot 的。
根據分治、遞迴的處理思想,我們可以用遞迴排序下標從 p 到 q-1 之間的資料和下標從 q+1 到 r 之間的資料,直到區間縮小為 1,就說明所有的資料都有序了。
歸併排序的處理過程是由下到上的,先處理子問題,然後再合併。
而快排正好相反,它的處理過程是由上到下的,先分割槽,然後再處理子問題。
歸併排序雖然是穩定的、時間複雜度為 o(nlogn) 的排序演算法,但是它是非原地排序演算法。歸併之所以是非原地排序演算法,主要原因是合併函式無法在原地執行。快速排序通過設計巧妙的原地分割槽函式,可以實現原地排序,解決了歸併排序占用太多記憶體的問題。
快排的時間複雜度也是 o(nlogn)
#include
using
namespace std;
void
swap
(int
*x,int
*y)int
partition
(int a,
int p,
int r)
}swap
(a[i]
,a[r]);
return i;
}void
quicksort
(int a,
int p,
int r)
intmain()
;quicksort
(num,0,
11);for
(int i =
0;i <
12;i++
)return0;
}
快速排序 歸併排序
感覺好久之前不寫這些基礎的東西忽然覺著,想複習一下,就簡單溫習一下排序的例子 package com.ruishenh.algoritmic public class sort static void printmsg int arrs system.out.println static int g...
快速排序,歸併排序
快速排序 quicksort 是對 氣泡排序的一種改進。設要排序的 陣列是a 0 a n 1 首先任意選取乙個資料 通常選用陣列的第乙個數 作為關鍵資料,然後將所有比它小的數都放到它前面,所有比它大的數都放到它後面,這個過程稱為一趟快速排序。需要注意的是,多個相同的值的相對位置也許會在演算法結束時產...
歸併排序,快速排序
快速排序實現 filename fastsort description author hcq createtime 2019 04 12 10 01 public class fastsort arrays.stream arr foreach v system.out.println 排序後 s...