排序方法总结

对之前学的排序方法做个总结:

一.冒泡排序 传送门.

冒泡排序(Bubble Sort)是一种较简单的排序算法。
主要原理:
比较相邻的元素。如果第一个比第二个大,就交换他们两个。 对每一对相邻元素做同样的工作,从开始第一对到结尾的最后一对。在这一点,最后的元素应该会是最大的数。 针对所有的元素重复以上的步骤,除了最后一个。 持续每次对越来越少的元素重复上面的步骤,直到没有任何一对数字需要比较。
很好理解
代码如下:

#include <cstdio>
#include <algorithm>
#include <iostream>
using namespace std;
const int MAXN = 10005;
int arr[MAXN];
int n;
void Bubble_Sort(int arr[],int len) {//冒泡排序 
	bool flag;
	for (int i = 1; i <= len - 1; i++) {
		flag = true;
		for (int j = 1; j <= n - i; j++) {
			if (arr[j] > arr[j + 1]) {
				swap(arr[j],arr[j + 1]);
				flag = false;
			}
		}
		if (flag) {
			break;
		}
	}
}
int main() {
	scanf("%d",&n);
	for (int i = 1; i <= n; i++) {
		scanf("%d",&arr[i]);
	}
	Bubble_Sort(arr,n);
	for (int i = 1; i <= n; i++) {
		printf("%d ",arr[i]);
	}
	return 0;
}

时间复杂度是O(n2 )。

二.快速排序 传送门.

快速排序(Quick Sort)是对冒泡排序的一种改进。
基本思想:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据都要小,然后再按此方法对这两部分数据分别进行快速排序。乍一看,不就是递归吗?
主要原理:设要排序的数组是a[l]到a[r],首先任意选取一个数据(这里选做数组中间值a[(l + r) / 2])作为关键数据,然后将所有比它小的数都放到它左边,所有比它大的数都放到它右边,这个过程称为一次快速排序。
一次快速排序的算法是:
1)设置两个变量i、j,排序开始的时候:i=l,j=r
2)以数组中间元素作为关键数据,赋值给mid,即mid=a[(l + r) / 2];
3)从j开始向前搜索,即由后开始向前搜索(j–),找到第一个小于mid的值a[j],将a[j]和a[i]的值交换;
4)从i开始向后搜索,即由前开始向后搜索(i++),找到第一个大于mid的a[i],将a[i]和a[j]的值交换;
5)重复第3、4步,直到i=j;
代码如下:

#include <cstdio>
#include <algorithm>
#include <iostream>
using namespace std;
const int MAXN = 10005;
int a[MAXN]; 
int n;
void Quick_Sort(int l,int r) {//快速排序 
	int i = l;
	int j = r;
	int mid = a[(l + r) / 2];
	while (i <= j) {
		while (a[i] < mid) {
			i++;
		}
		while (a[j] > mid) {
			j--;
		}
		if (i <= j) {
			swap(a[i],a[j]);
			i++;
			j--;
		}
	}
	if (j > l) {
		Quick_Sort(l,j);
	}
	if (i < r) {
		Quick_Sort(i,r);
	}
}
int main() {
	scanf("%d",&n);
	for (int i = 1; i <= n; i++) {
		scanf("%d",&a[i]);
	}
	Quick_Sort(1,n);
	for (int i = 1; i <= n; i++) {
		printf("%d ",a[i]);
	}
	return 0;
}

时间复杂度是O(n log n)。

三.选择排序 传送门.

选择排序(Selection Sort)是一种简单直观的排序算法。
主要思想:
对比数组中前一个元素跟后一个元素的大小,如果后面的元素比前面的元素小,则用一个变量index来记住他的位置,接着第二次比较,前面“后一个元素”现变成了“前一个元素”,继续跟他的“后一个元素”进行比较,如果后面的元素比他要小则用变量index记住它在数组中的位置,等到循环结束的时候,我们应该找到了最小的那个数的下标了,然后进行判断,如果这个元素的下标不是第一个元素的下标,就让第一个元素跟他交换一下值,这样就找到整个数组中最小的数了。然后找到数组中第二小的数,让他跟数组中第二个元素交换一下值,以此类推。
代码如下:

#include <cstdio>
#include <algorithm>
#include <iostream>
using namespace std;
const int MAXN = 10005;
int arr[MAXN];
int n;
void Select_Sort(int arr[],int len) {//选择排序 
	int index;
	for (int i = 1; i <= len - 1; i++) {
		index = i;
		for (int j = i + 1; j <= len; j++) {
			if (arr[index] > arr[j]) {
				index = j;
			}
		}
		if (i != index) {
			swap(arr[i],arr[index]);
		}
	}
}
int main() {
	scanf("%d",&n);
	for (int i = 1; i <= n; i++) {
		scanf("%d",&arr[i]);
	}
	Select_Sort(arr,n);
	for (int i = 1; i <= n; i++) {
		printf("%d ",arr[i]);
	}
	return 0;
}

时间复杂度和冒泡排序一样,是O(n2)。

四.桶排序 传送门.

桶排序 (Bucket Sort) 就是所谓的箱排序。
桶排序是计数排序的扩展版本,计数排序可以看成每个桶只存储相同元素,而桶排序每个桶存储一定范围的元素,通过映射函数,将待排序数组中的元素映射到各个对应的桶中,对每个桶中的元素进行排序,最后将非空桶中的元素逐个放入原序列中。
代码如下:

#include <cstdio>
#include <algorithm>
#include <iostream>
using namespace std;
const int MAXN = 10005;
int arr[MAXN],bucket[MAXN];
int n;
int maxn = INT_MIN,minn = INT_MAX;
void Bucket_Sort(int arr[],int len) {//桶排序 
	for (int i = 1; i <= len; i++) {
		bucket[arr[i]]++;
	}
	for (int i = minn; i <= maxn; i++) {
		while (bucket[i]) {
			printf("%d ",i);
			bucket[i]--;
		}
	}
}
int main() {
	scanf("%d",&n);
	for (int i = 1; i <= n; i++) {
		scanf("%d",&arr[i]);
		if (arr[i] >= maxn) {
			maxn = arr[i];
		}
		if (arr[i] <= minn) {
			minn = arr[i];
		}
	}
	Bucket_Sort(arr,n);
	return 0;
}

桶排序使用线性时间,复杂度是O(n)。(但是很占空间)

下面给出其他排序方法的比较结果
各大排序方法比较
从上图来看,堆排序应该是最优的排序算法(无论什么情况,复杂度都是O(n log n)),但在大数据面前, 堆排序则不如快排, 所以说, 快速排序才应该是最优的排序方法。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值