文章目录
1.选择排序
- 直接选择排序
- 堆排序
2.直接选择排序
1)基本思想
每次从无序区间里选出最小的数,然后插入到无序区间的begin,(数组右边是有序,左边是无序),begin加加,这时begin以前的都是升序的,重复前面操作直到begin和end相遇,至此所有记录有序。
[图片为转载博主一像素]
2)时间复杂度:O(n2)
3)空间复杂度O(1)
4)不稳定
5)代码
a.普通版本
void Swap(int *a, int *b)
{
int temp = *a;
*a = *b;
*b = temp;
}
void Select(int num[], int len)
{
if (num == NULL || len <= 0)
return;
int i = 0;
//1.确定循环躺数
for (; i < len - 1; i++)
{
int minindex = i;
int j = i + 1;
//2.找到无序区的最小值
for (; j < len; j++)
{
if (num[minindex] > num[j])
{
minindex = j;
}
}
//与无序区第一个元素交换
if (minindex != i)
Swap(&num[minindex], &num[i]);
}
}
b.算法优化
一次选两个,一个最大的,一个最小的.
void SelectSort(int arr[], int len)
{
int left = 0;
int right = len - 1;
while (left < right)
{
int max = left;//记录无序区最大元素下标
int min = left;//记录无序区最小元素下标
int j = 0;
for (j = left + 1; j <= right; j++)
{
//找最大元素下标
if (arr[j] < arr[min])
{
min = j;
}
//找最小元素下标
if (arr[j]>arr[max])
{
max = j;
}
}
if (min != left)
{
int tmp = arr[left];
arr[left] = arr[min];
arr[min] = tmp;
}
//如果最大元素下标是left,前面已经和最小元素交换了,此时最大元素下标应该是min
if (max == left)
{
max = min;
}
if (max != right)
{
int tmp = arr[right];
arr[right] = arr[max];
arr[max] = tmp;
}
left++;
right--;
}
}
2.堆排序
1)基本思想
- 创建堆:升序->大堆(建大堆:建大堆是因为把堆顶最大的和堆尾交换后,只用对堆顶进行一次向下调整就行,其他子树还是大堆,注意调整的范围要减减,;如果是小堆,那么堆顶是最小得,那么要对后面所有的数重新建小堆,就复杂了),降序->小堆
- 执行如下步骤,直到数组为空
- 把栈顶元素和当前最堆的最后一个元素交换
- 堆元素个数减1
- 再次调整根节点
[图片为转载博主一像素]
2)时间复杂度:O(n*log2n)
3)空间复杂度:O(1)
4)不稳定
5)代码
#include<stdio.h>
void AdjustDown(int* num, int n, int parent)
{
if (num == NULL || n <= 0)
return;
int child = 2 * parent + 1;
while (child < n)
{
//处理让child指向左右孩子中较大的哪一个
if ((child + 1 < n) && (num[child] < num[child + 1]))
child++;
//比较交换并调整
if (num[child]>num[parent])
{
Swap(&num[child], &num[parent]);
parent = child;
child = 2 * parent + 1;
}
else
{
break;
}
}
}
//堆排序
void HeapSort(int* num, int len)
{
if (num == NULL || len <= 0)
return;
//1.建堆(升序->大堆,降序->小堆)
for (int i = (2 * len - 2) / 2; i >= 0; i--)
{
AdjustDown(num, len, i);
}
//2.交换最后一个元素和第一个元素
int end = len - 1;
while (end > 0)
{
Swap(&num[0], &num[end]);
AdjustDown(num, end, 0);
--end;
}
}