排序算法
冒泡排序
两层for循环控制 一层外部整体 一层局部调整顺序
优化:
如果局部检测 第一次检测发现全部是顺序的 直接break
class Solution {
public:
void bubble_sort(vector<int>& nums) {
int size = nums.size();
bool flag = false;
for (int i = 0; i < size - 1; i++) {
flag = false;
for (int j = 0; j < size - 1 - i; j++) {
if (nums[j] > nums[j + 1]) {
swap(nums[j], nums[j + 1]);
flag = true;
}
}
if (!flag) break;
}
}
vector<int> sortArray(vector<int>& nums) {
bubble_sort(nums);
return nums;
}
};
快速排序
随机选取一个数(x = rand() % len + startIndex)作为基准;
把比基准小的数交换到前面,比基准大的数交换到后面;
对左右区间递归重复。
时间复杂度nlogn,空间复杂度logn
class Solution {
public:
void quick_sort(vector<int>& nums, int begin, int end) {
if (begin >= end) return;
int x = rand() % (end - begin + 1) + begin;
int l = begin, r = end;
swap(nums[l], nums[x]);
int val = nums[l];
while (l < r) {
while (l < r && nums[r] > val) r--;
if (l < r) {
nums[l] = nums[r];
l++;
}
while (l < r && nums[l] < val) l++;
if (l < r) {
nums[r] = nums[l];
r--;
}
}
nums[l] = val;
quick_sort(nums, begin, l - 1);
quick_sort(nums, l + 1, end);
}
vector<int> sortArray(vector<int>& nums) {
quick_sort(nums, 0, nums.size() - 1);
return nums;
}
};
堆排序
先在原先数组的基础上构造大根堆(时间复杂度nlogn);
再依次弹出最大元素(每次弹出的时间复杂度为logk,k为当前大根堆中元素数目)。
时间复杂度nlogn,空间复杂度1
class Solution {
public:
void sift_down(vector<int>& nums, int i, int size) {
int val = nums[i];
while (i < size / 2) {
int child = i * 2 + 1;
if (child + 1 < size && nums[child + 1] > nums[child]) {
child = child + 1;
}
if (nums[child] > val) {
nums[i] = nums[child];
i = child;
} else {
break;
}
}
nums[i] = val;
}
void heap_sort(vector<int>& nums, int size) {
int n = size - 1;
for (int i = (n - 1) / 2; i >= 0; i--) {
sift_down(nums, i, size);
}
for (int i = n; i >= 0; i--) {
int tmp = nums[0];
nums[0] = nums[i];
nums[i] = tmp;
sift_down(nums, 0, i);
}
}
vector<int> sortArray(vector<int>& nums) {
heap_sort(nums, nums.size());
return nums;
}
};
归并排序
将无序数组拆分,排序后再合并成大的有序数组。
时间复杂度nlogn,空间复杂度n
class Solution {
public:
void merge_sort(vector<int>& nums, int begin, int end, vector<int>& tmp) {
if (begin >= end) return;
int mid = begin + (end - begin) / 2;
merge_sort(nums, begin, mid, tmp);
merge_sort(nums, mid + 1, end, tmp);
int index = 0;
int i = begin;
int j = mid + 1;
while (i <= mid && j <= end) {
if (nums[i] < nums[j]) {
tmp[index++] = nums[i++];
} else {
tmp[index++] = nums[j++];
}
}
while (i <= mid) {
tmp[index++] = nums[i++];
}
while (j <= end) {
tmp[index++] = nums[j++];
}
for (int i = begin, j = 0; i <= end; i++, j++) {
nums[i] = tmp[j];
}
}
vector<int> sortArray(vector<int>& nums) {
int size = nums.size();
vector<int> tmp(size);
merge_sort(nums, 0, size - 1, tmp);
return nums;
}
};