#include<iostream>
#include<assert.h>
//所有排序默认升序
using namespace std;
//普通插入排序
void InsertSort(int* array, size_t size)
{
assert(array);
for (size_t i = 1; i < size; ++i)
{
int tmp = array[i];
int j = i - 1;
for (; j >= 0;--j)
{
if (tmp < array[j])
{
array[j + 1] = array[j];
}
else
{
break;
}
}
array[j+1] = tmp;
}
}
二分·插入排序2
void InsertSort_P(int* array, size_t size)
{
assert(array);
for (size_t i = 1; i < size; ++i)
{
//插入第i单个元素
int temp = array[i];
int left = 0;
int right = i;
// 找位置
while (left < right)
{
int mid = left + (right - left) / 2;
if (array[mid] <= temp)
{
left = mid + 1;
}
else
{
right = mid;
}
}
// 搬移数据
for (int end = i - 1; end >= left; end--)
{
array[end + 1] = array[end];
}
array[left] = temp;
}
}
二分·插入排序2
//void InsertSort_P(int* array, size_t size)
//{
// assert(array);
//
// for (int i = 1; i < size; ++i)
// {
// //插入第i单个元素
// int temp = array[i];
// int left = 0;
// int right = i;
//
// // 找位置
// while (left < right)
// {
// int mid = left + (right - left) / 2;
// if (array[mid] <= temp)
// {
// left = mid + 1;
// }
// else
// {
// right = mid;
// }
// }
//
// // 搬移数据
// for (int end = i - 1; end >= left; end--)
// {
// array[end + 1] = array[end];
// }
//
// array[left] = temp;
// }
//}
//二分·插入排序1
void InsertSortHalf(int *arr,size_t size)
{
assert(arr);
for (size_t i = 1; i < size; ++i)
{
int tmp = arr[i];
if (tmp < arr[i - 1])
{
int left = 0;
int right = i - 1;
//
while (left <= right)
{
int mid = left + (right - left) / 2;
if (tmp < arr[mid])
right = mid - 1;
else
left = mid + 1;
}
for (int j = i - 1; j >= right + 1; --j)
arr[j + 1] = arr[j];
arr[right + 1] = tmp;
}
}
}
//希尔排序(插入排序的一种)
void ShellSort(int* array, size_t size)
{
assert(array);
int gap = size;
while (gap > 1 )
{
gap = gap / 3 + 1;
for (size_t i = gap; i < size; ++i)
{
if (array[i] < array[i - gap])
{
int tmp = array[i];
int j = i - gap;
for (; j >= 0 && tmp < array[j]; j -= gap)
{
array[gap + j] = array[j];
}
array[j + gap] = tmp;
}
}
}
}
//简单选择排序:每次找一个最值,放在最前面或者最后面,同时缩小区间
// 比较n+n-1+n-2+.. 共n(n-1)/2次 时间复杂度为O(n2);
void SelectSort(int* array, size_t size)
{
assert(array);
int end = size-1;
while (--end)
{
int maxpos = 0;
int i = 1;
for (; i <= end; ++i)
{
if (array[i]>array[maxpos])
{
maxpos = i;
}
}
if (end != maxpos)
swap(array[end], array[maxpos]);
}
}
//改进的选择排序:同时找最大值和最小值
//:这个代码是有问题的 :倘若最大值在数组最前面,最小值在数组最后面,
//那个第一次找到的最大值下标就是0,最小值下标就是size-1:
//然后执行交换,交换了两次,两个值又回到了原处,那么一开始就错了
//要改进的话,每次发现比这个min小的就直接交换即可,但是这么实现就跟选择排序的思想背道而驰故此不实现
/这是一段错误的代码/
void SelectSortDou(int* array, size_t size)
{
assert(array);
int end = size-1;
int begin = 0;
while (begin <= end)
{
int maxpos = end;
int minpos = begin;
for (int i = begin; i <= end; ++i)
{
if (array[i]>array[maxpos])
{
maxpos = i;
}
if (array[i]<array[minpos])
{
minpos = i;
}
}
if (end != maxpos)
swap(array[end], array[maxpos]);//问题出在这里
if (begin!=minpos)
swap(array[begin], array[minpos]);//问题出在这里
begin++;
end--;
}
}
//上面是一段错误的代码///
//改进的选择排序:树形选择排序,也叫锦标赛排序(未实现)
void adjustDown(int* array, int i,int end)
{
int child = 2 * i + 1;
while (child <= end)
{
if ((child + 1 <= end) && (array[child + 1] > array[child]))
child += 1;
if (array[child] > array[i])
swap(array[child], array[i]);
i = child;
child = child * 2 + 1;
}
}
//对树形选择排序再进行改进:堆排序,这里要创建最大堆
void HeapSort(int* array, size_t size)
{
assert(array);
//对整个数组进行一次堆排列
for (int i = (size - 1) / 2; i >= 0; --i)
{
adjustDown(array, i, size-1);
}
//每次把最大的一个放在数组后面,同时堆排序范围减少1
for (int i = (size - 1); i > 0; --i)
{
swap(array[i], array[0]);
adjustDown(array, 0, i-1);
}
}
void pri(int *arr,size_t size)
{
for (size_t i = 0; i < size; ++i)
{
cout << arr[i]<<" ";
}
cout << endl;
}
//这里面都是插入排序,
void test1()
{
int arr[] = { 21, 18, 49, 25, 16, 8,21,35,99,5,21 };
//InsertSort(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
//InsertSortHalf(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
//ShellSort(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
}
//这些都是选择排序
void test2()
{
int arr[] = { 8, 21, 35, 99, 5, 21,21, 18, 49, 25, 16, 1,19,88,53};
//int arr[] = { 1, 5, 8, 16, 18, 19, 21, 21, 21, 25, 35, 49, 53, 88, 99 };
//SelectSort(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
//SelectSortDou(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
//HeapSort(arr, sizeof(arr) / sizeof(int));
//pri(arr, sizeof(arr) / sizeof(int));
}
int main()
{
//test1();
test2();
system("pause");
return 0;
}
排序算法(1):插入排序,选择排序,希尔排序,堆排序
最新推荐文章于 2024-07-28 11:02:31 发布