|
請介紹下C++中的std::sort算法?
回答重點
std::sort 非常高效,它不單純是快速排序,而是使用了一種名為 introspective sort(內(nèi)省排序)的算法。
內(nèi)省排序是快速排序、堆排序和插入排序的結(jié)合體,它結(jié)合這些算法優(yōu)點的同時避免它們的缺點,特別是快速排序在最壞情況下的性能下降問題。
注意:本題介紹,僅限于GCC的源碼實現(xiàn)。
擴展知識快速排序:內(nèi)省排序首先使用快速排序算法。利用快速排序分而治之的特點,通過選取一個pivot元素,將數(shù)組分為兩個子數(shù)組,一個包含小于pivot的元素,另一個包含大于pivot的元素,然后遞歸地對這兩個子數(shù)組進行快速排序?焖倥判蛟谄骄闆r下非常高效,時間復(fù)雜度為 O(n log n)。
/// This is a helper function for the sort routine.template typename _RandomAccessIterator, typename _Size, typename _Compare>_GLIBCXX20_CONSTEXPR void__introsort_loop(_RandomAccessIterator __first, _RandomAccessIterator __last, _Size __depth_limit, _Compare __comp) { while (__last - __first > int(_S_threshold)) { if (__depth_limit == 0) { std::__partial_sort(__first, __last, __last, __comp); return; } --__depth_limit; _RandomAccessIterator __cut = std::__unguarded_partition_pivot(__first, __last, __comp); std::__introsort_loop(__cut, __last, __depth_limit, __comp); __last = __cut; }}
// sort
template typename _RandomAccessIterator, typename _Compare>_GLIBCXX20_CONSTEXPR inline void __sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) { if (__first != __last) { std::__introsort_loop(__first, __last, std::__lg(__last - __first) * 2, __comp); std::__final_insertion_sort(__first, __last, __comp); }}內(nèi)省排序:通過限制快速排序遞歸深度,避免其最壞情況的性能問題。遞歸深度的限制基于輸入數(shù)組的大小,通常是對數(shù)組長度取對數(shù)然后乘以一個常數(shù)(在 GCC 實現(xiàn)中是 2 * log(len))。如果排序過程中遞歸深度超過了這個限制,算法會切換到堆排序。
/// This is a helper function for the sort routine.template typename _RandomAccessIterator, typename _Size, typename _Compare>_GLIBCXX20_CONSTEXPR void__introsort_loop(_RandomAccessIterator __first, _RandomAccessIterator __last, _Size __depth_limit, _Compare __comp) { while (__last - __first > int(_S_threshold)) { if (__depth_limit == 0) { std::__partial_sort(__first, __last, __last, __comp); return; } --__depth_limit; _RandomAccessIterator __cut = std::__unguarded_partition_pivot(__first, __last, __comp); std::__introsort_loop(__cut, __last, __depth_limit, __comp); __last = __cut; }}
// sort
template typename _RandomAccessIterator, typename _Compare>_GLIBCXX20_CONSTEXPR inline void __sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) { if (__first != __last) { std::__introsort_loop(__first, __last, std::__lg(__last - __first) * 2, __comp); std::__final_insertion_sort(__first, __last, __comp); }}堆排序:當(dāng)快速排序的遞歸深度超過限制時,內(nèi)省排序會切換到堆排序,保證最壞情況下的時間復(fù)雜度為 O(n log n)。堆排序不依賴于數(shù)據(jù)的初始排列,因此它的性能無論在最好、平均和最壞情況下都是穩(wěn)定的。
/// This is a helper function for the sort routine.template typename _RandomAccessIterator, typename _Size, typename _Compare>_GLIBCXX20_CONSTEXPR void__introsort_loop(_RandomAccessIterator __first, _RandomAccessIterator __last, _Size __depth_limit, _Compare __comp) { while (__last - __first > int(_S_threshold)) { if (__depth_limit == 0) { std::__partial_sort(__first, __last, __last, __comp); return; } --__depth_limit; _RandomAccessIterator __cut = std::__unguarded_partition_pivot(__first, __last, __comp); std::__introsort_loop(__cut, __last, __depth_limit, __comp); __last = __cut; }}插入排序:最后,當(dāng)數(shù)組的大小減小到一定程度時,內(nèi)省排序會使用插入排序來處理小數(shù)組。插入排序在小數(shù)組上非常高效,盡管它的平均和最壞情況時間復(fù)雜度為 O(n^2),但在數(shù)據(jù)量小的情況下,這種復(fù)雜度不是問題。此外,插入排序是穩(wěn)定的,可以保持等值元素的相對順序。
/// This is a helper function for the sort routine.template typename _RandomAccessIterator, typename _Compare>_GLIBCXX20_CONSTEXPR void __final_insertion_sort(_RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp) { if (__last - __first > int(_S_threshold)) { std::__insertion_sort(__first, __first + int(_S_threshold), __comp); std::__unguarded_insertion_sort(__first + int(_S_threshold), __last, __comp); } else std::__insertion_sort(__first, __last, __comp);}——EOF——你好,我是飛宇。日常分享C/C++、計算機學(xué)習(xí)經(jīng)驗、工作體會,歡迎點擊此處查看我以前的學(xué)習(xí)筆記&經(jīng)驗&分享的資源。
我組建了一些社群一起交流,群里有大牛也有小白,如果你有意可以一起進群交流。
od4ehbbfuu564032156258.png (195.91 KB, 下載次數(shù): 1)
下載附件
保存到相冊
od4ehbbfuu564032156258.png
2024-11-28 01:26 上傳
歡迎你添加我的微信,我拉你進技術(shù)交流群。此外,我也會經(jīng)常在微信上分享一些計算機學(xué)習(xí)經(jīng)驗以及工作體驗,還有一些內(nèi)推機會。
2tcbqhvr1as64032156358.png (281.08 KB, 下載次數(shù): 1)
下載附件
保存到相冊
2tcbqhvr1as64032156358.png
2024-11-28 01:26 上傳
加個微信,打開另一扇窗
↓推薦關(guān)注↓
感謝你的分享,點贊,在看三連
jj2fggiqx5z64032156458.gif (88.16 KB, 下載次數(shù): 0)
下載附件
保存到相冊
jj2fggiqx5z64032156458.gif
2024-11-28 01:26 上傳
|
|