直接插入排序:
- 最坏时间复杂度 O(n^2)
- 平均时间复杂度 O(n^2/4)
- 空间复杂度 O(1)
- 稳定
- 改进:折半插入(因为折半查找比顺序查找性能好,可以减少比较次数,但移动次数没有减少)
2路插入、希尔排序… - 每次要处理的元素的左边都是有序序列
希尔排序:
- 时间复杂度O(n^1.25) 与所取的增量序列有关。
- 空间复杂度 O(1)
- 要求:各增量互素,且最小增量为1;顺序存储
- 不稳定
冒泡排序:
- 时间复杂度 O(n^2)
- 平均时间复杂度 O(n^2/2)
- 空间复杂度 O(1)
- 稳定
- 缺点:没有利用已排序的结果
- 注意:不要忘了设置flag(一趟排序没有交换表示已经排好序)
堆排序:
- 时间复杂度 O(nlogn)
- 空间复杂度 O(1)
- 不稳定
- 适用于 n 较大的情况
- 注意:若从小到大排序,则设置小顶堆(每个结点的值都比左右结点的值小),每次取根结点,并更新最小堆。
快速排序:
- 思想:分治策略
- 最坏时间复杂度:O(n^2)
- 平均、最好时间复杂度:O(nlogn) (内排序中最好的)
空间复杂度:O(logn)~O(n) (递归用栈,二叉树的高度) - 不稳定
- 最适合:数据完全无序,数据量大
基数排序:
- 思想:桶排序。
- 特点:非比较、多关键字
- 对于一位数的整数进行排序的时间复杂度是O(n),非常适合对一位数的整数进行排序
桶排序
- 将元素根据规则分组,每一组采用快排、插入排序等算法进行排序,然后再按照次序将所有元素合并,就可以得到一个有序序列
#include <iostream>
#include <stdlib.h>
using namespace std;
void insert_sort(int arr[], int n)
{
int temp;
for (int i = 1; i < n; i++)
{
temp = arr[i];
int k = i - 1;
for (; k >= 0; k--)
{
if (arr[k] > temp)
{
arr[k + 1] = arr[k];
}
else
break;
}
arr[k + 1] = temp;
}
}
void shell_sort(int arr[], int n)
{
int d = n / 2;
while (d > 0)
{
int temp;
for (int i = d; i < n; i += d)
{
temp = arr[i];
int k = i - 1;
for (; k >= 0; k--)
{
if (arr[k] > temp)
{
arr[k + 1] = arr[k];
}
else
break;
}
arr[k + 1] = temp;
}
d /= 2;
}
}
void bubble_sort(int arr[], int n)
{
int temp;
n--;
bool flag = true;
for (int i = 0; i < n; i++)
{
for (int j = 0; j < n - i; j++)
{
if (arr[j] > arr[j + 1])
{
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
flag = false;
}
}
if (flag)
break;
flag = true;
}
}
void heapfy(int arr[], int node, int n)
{
if (node > n / 2 || node < 0)
return;
int lChild = node * 2 + 1;
int rChild = node * 2 + 2;
int min = arr[node];
if (rChild < n && min > arr[rChild])
min = arr[rChild];
if (lChild < n && min > arr[lChild])
min = arr[lChild];
if (min != arr[node])
{
if (rChild < n && min == arr[rChild])
{
arr[rChild] = arr[node];
heapfy(arr, rChild, n);
}
else if (lChild < n && min == arr[lChild])
{
arr[lChild] = arr[node];
heapfy(arr, lChild, n);
}
arr[node] = min;
}
}
void heap_sort(int arr[], int n)
{
for (int i = n; i > 0; i--)
{
for (int k = i / 2; k >= 0; k--)
{
heapfy(arr, k, i);
}
printf("%d ", arr[0]);
arr[0] = arr[i - 1];
}
}
int partition(int arr[], int low, int high)
{
int index = high;
int base = arr[high];
while (low < high)
{
while (arr[low] <= base && low < high)
low++;
while (arr[high] >= base && low < high)
high--;
if (low < high)
{
int temp = arr[low];
arr[low] = arr[high];
arr[high] = temp;
}
}
if (index != low)
{
arr[index] = arr[low];
arr[low] = base;
}
return low;
}
void quick_sort(int arr[], int low, int high)
{
int position;
if (low < high)
{
position = partition(arr, low, high);
quick_sort(arr, low, position - 1);
quick_sort(arr, position + 1, high);
}
}
bool is_order(int arr[], int n)
{
for (int i = 0; i < n - 1; i++)
{
if (arr[i] > arr[i + 1])
return false;
}
return true;
}
int main()
{
int n;
scanf("%d", &n);
int arr[n];
for (int i = 0; i < n; i++)
{
arr[i] = int(rand());
}
shell_sort(arr, n);
for (int i = 0; i < n; i++)
{
printf("%d ", arr[i]);
}
}