排序算法小结:C++实现
#include<vector> #include<iostream> //排序算法的稳定性:对于相同的关键字,排序之前的位置和排序之后的位置相同,则称为稳定排序,否则不稳定排序。 //归并排序:基本思想为:先分解再合并,在合并的过程中进行排序; //稳定排序;平均时间复杂度为:O(nlogn); 最好时间复杂度O(nlogn);最好时间复杂度O(nlogn);空间复杂度O(n); void Meger(std::vector<int> &data, int begin, int mid,int end) { if (begin == end) { return; } int length = end - begin+1; std::vector<int> temp(length); int i = begin; int j = mid+1; int k = 0; while (i <= mid&&j <= end) { if (data[i] <= data[j]) { temp[k++] = data[i++]; } else { temp[k++] = data[j++]; } } while (i <= mid) { temp[k++] = data[i++]; } while (j <= end) { temp[k++] = data[j++]; } for (i = 0; i < k; i++) { data[begin + i] = temp[i]; } } void Divide(std::vector<int> &data, int begin, int end) { if (begin>=end) { return; } int mid = (begin + end) / 2; Divide(data, begin, mid); Divide(data, mid+1, end); Meger(data, begin,mid, end); } void Meger_Sort(std::vector<int> &data) { if (data.empty()) { return; } Divide(data, 0, data.size()-1); for (auto each : data) { std::cout << each << "\n"; } } //Quick Sort: 找到中间分割点,根据中间分割点进行排序,再递归。 //不稳定;平均时间复杂度O(nlogn); 最好时间复杂度O(nlogn);最坏时间复杂度O(n^2);空间复杂度O(logn) int Partition(std::vector<int> &vec, int left, int right) { int X = vec[left]; while (left < right) { while (vec[right] > X) { right--; } if (left < right) { vec[left] = vec[right]; left++; } while (vec[left] <= X) { left++; } if (left < right) { vec[right] = vec[left]; right--; } } vec[right] = X; return right; } void Quick_Sort(std::vector<int> &vec,int left,int right) { if (vec.empty()) { return; } if (left < right) { int p = Partition(vec, left, right); Quick_Sort(vec, left, p - 1); Quick_Sort(vec, p + 1, right); } } //选择排序 //不稳定;平均时间复杂度O(n^2); 最好时间复杂度O(n^2);最坏时间复杂度O(n^2);空间复杂度O(1) void Select_Sort(std::vector<int> &vec) { for (int i = 0; i < vec.size()-1; i++) { int mini_index = i; for (int j = i+1; j < vec.size(); j++) { if (vec[j] < vec[mini_index]) { mini_index = j; } } std::swap(vec[i], vec[mini_index]); } } //冒泡排序 //稳定;平均时间复杂度O(n^2); 最好时间复杂度O(n);最坏时间复杂度O(n^2);空间复杂度O(1) void Bubble_Sort(std::vector<int> &vec) { //普通版本; for (int i = 0; i < vec.size(); ++i) { for (int j = 1; j < vec.size() - i; ++j) { if (vec[j-1] > vec[j]) { std::swap(vec[j-1], vec[j]); } } } } void fast_Bubble_Sort(std::vector<int> &vec) { //fast 版本; int flag = vec.size(); int len = flag; while (flag) { flag = 0; for (int i = 1; i < len; ++i) { if (vec[i - 1] > vec[i]) { std::swap(vec[i - 1], vec[i]); } flag = i; } len = flag; } } //插入排序 //稳定;平均时间复杂度O(n^2); 最好时间复杂度O(n);最坏时间复杂度O(n^2);空间复杂度O(1) void Insert_Sort(std::vector<int> &vec) { for (int i = 1; i < vec.size(); ++i) { int temp = vec.at(i); int j = i - 1; while (j >= 0&&vec.at(j) > temp) { vec[j + 1] = vec[j]; j--; } vec[j+1] = temp; } } //堆排序:先建立一个大根堆,然后将堆顶元素和队列尾的元素进行交换,这样就等于大元素放到队尾了每次交换, // 需要对堆进行调整。 //不稳定;平均时间复杂度O(nlogn); 最好时间复杂度O(nlogn);最坏时间复杂度O(nlogn);空间复杂度O(1) void adjustHeap(std::vector<int> &vec, int index,int length) { int temp = vec[index]; //首先将该元素与其左子节点元素进行比较 for (int k = 2 * index + 1; k < length; k = 2 * k + 1) { //对左右节点进行比较,如果右节点比较大,更换成右节点 if (k + 1 < length&&vec[k] < vec[k + 1]) { k++; } if (vec[k] >temp) { vec[index] = vec[k]; index = k; } else { break; } } vec[index] = temp; } void HeapSort(std::vector<int> &vec) { int length = vec.size(); if (length == 0) { return; } //构建最大堆; for (int i = length / 2 - 1; i >= 0; i--) { adjustHeap(vec, i, length); } //大堆顶元素逐个与末尾元素进行交换。 for (int i = length - 1; i > 0; i--) { std::swap(vec[i], vec[0]); adjustHeap(vec, 0,i); } } //Main 函数测试部门; int main() { std::vector<int> vec = { 10,6,1,9,3,11,7,2,12,8,5,4,13 }; HeapSort(vec); for (auto each : vec) { std::cout << each << "\n"; } return 0; }