【算法】三大简单、慢速排序算法及C++实现

分类及原理

直接插入排序

模拟排序扑克牌,新牌<旧牌,旧牌依次后移

直接选择排序

从第一个位置开始比较,找出最小的,和第一个位置互换,开始下一轮。

冒泡排序

从左到右,数组中相邻的两个元素进行比较,将较大的放到后面。每一趟排序,最大的数移到最后面,每一趟排序以此交换的次数会减一,因为每一趟排序后,有一个数已经达到指定位置
eg:

趟数元素
05 4 3 2 1
14 5 3 2 1
14 3 5 2 1
14 3 2 5 1
14 3 2 1 5 第一趟排序5归位,交换次数:n-1 = 4
23 4 2 1 5
23 2 4 1 5
23 2 1 4 5第二趟排序4归位,交换次数:4-1=3
32 3 1 4 5
32 1 3 4 5第三趟排序3归位,交换次数:3-1=2
41 2 3 4 5第四趟排序2归位,交换次数:2-1=1

稳定性定义

举个例子:5,8,5,2,9 我们知道第一遍选择排序第一个元素5会和2交换,那么原序列中2个5的相对位置前后顺序就破坏了

优缺点

这三种算法的优点简单,缺点慢

类型平均最好最坏辅助存储稳定性
直接插入O( n 2 n^2 n2)O(n)O( n 2 ) n^2) n2)1稳定
直接选择O( n 2 n^2 n2) O ( n 2 O(n^2 O(n2)O( n 2 ) n^2) n2)1不稳定
冒泡O( n 2 n^2 n2)O(n)O( n 2 ) n^2) n2)1稳定

C++实现

插入排序

void insert_sort(int* array, int len) {
	for (int i = 1; i < len; i++) {
		for (int j = i - 1; j >= 0 && array[j] > array[j+1]; j--) {
			swap(array[j], array[j + 1]);
		}
	}
}

直接选择排序

//选择排序
void select_sort(int array[], int array_len)
{
	for (int i = 0; i < array_len; i++)
	{
		int array_min = array[i];
		int array_min_index = i;
		for (int j = i + 1; j < array_len; j++)//每次选出一个最小值
		{
			if (array[j] < array_min)
			{
				array_min = array[j];
				array_min_index = j;
			}
		}
		//最小值放到前面,可能会破坏相等数的前后顺序,不稳定
		int tmp = array[array_min_index];
		array[array_min_index] = array[i];
		array[i] = tmp;
	}
}

冒泡排序

冒泡排序普通版本

void bubble_sort(int array[], int array_len)
{
	for(int i = 0; i < array_len; i++)
	{//每次外循环,把当前最大的数移到最后
		for(int j = 0; j < array_len - i - 1;j++)
		{//内循环,两两比较,每次减少一次比较
			if(array[j] > array[j + 1])
			{
				int tmp = array[j];
				array[j] = array[j + 1];
				array[j + 1] = tmp;
			}
		}
	}
}

冒泡排序改进版本(加标志位,提前结束)

void bubble_sort(int* array, int len) {
	for (int end = len - 1; end > 0; end--) {
		bool is_sort = true;
		for (int j = 0; j < end; j++) {
			if (array[j] > array[j + 1]) {
				int tmp = array[j];
				array[j] = array[j + 1];
				array[j + 1] = tmp;
				is_sort = false;
			}
		}
		if(is_sort)
			break;
	}
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值