冒泡排序
原理
升序:冒泡排序的基本原理是从左往右遍历数组,如果是数组中相邻的两个数,且左边的大于右边的,就将两者交换位置。不断执行此过程,最后就会得到一个升序排列的数组。
实例
假设有一个数组,其中元素从左往右分别为:0,2,1,10,9,4,2,8,则其冒泡排序的过程如下:
由上面的过程我们可知,每次遍历后的结果如下:
实现(冒泡排序的升序)
#include<iostream>
using namespace std;
template<class T>
void bubbleSort(T *a,const int len){ //len表示a的长度
for(int i = 0;i<len;i++){ //遍历数组的次数
for(int j=0;j<(len-i);j++){ //遍历数组,终止结点为数组的长度-遍历的次数再减1,因为数组的最大下标为长度-1
if(a[j]>a[j+1])std::swap(a[j],a[j+1]);//如果左边相邻的数大于右边的,就将两者交换位置,如果需要降序排列,则只需要将if中的“>”变为“<”即可。
}
}
}
int main(){
int a[] = {0,2,1,10,9,4,2,8};
bubbleSort(a,8);
for(int i=0;i<8;i++){
cout<<a[i]<<";";
}
return 0;
}
运行结果为:
选择排序
原理
每次遍历数组,选出最小的元素,然后与下标为遍历的次数减一的元素进行交换,与冒泡排序不同的是,选择排序是直接找出最小的进行交换,而冒泡则是每比较一次,只要不符合要求,就交换。
实例(升序)
假设有一个数组,其中元素为:9,6,8,3,5,7,0,2,1
选择排序的过程为:
我们选择第一次遍历进行详细说明(第一次遍历的过程):
遍历完成后,key已经指向了值最小的元素的下标,key为6,此时只需要交换a[0]和a[6]的值就可以了,至此,第一次遍历彻底完成。
注: 如果需要降序排列,只需要将key指向最大值的下标即可,其他过程不变。
实现
#include<iostream>
using namespace std;
template<class T>
void selectSort(T *a,const int n){//n表示a的长度
for(int i=0;i<n;i++){ //遍历a的次数,从0开始;如果此处从1开始,则在下面交换时要给i-1
int key = i; //假设下标为i的元素是最小的,我们让key指向他
for(int j=i;j<n;j++){
if(a[key]>a[j]){
key = j;
}
}
std::swap(a[key],a[i]); //将最小值与i进行交换,即上面所说的最后的交换过程。
}
}
int main(){
int a[] = {9,6,8,3,5,7,0,2,1};
selectSort(a,9);
for(int i=0;i<9;i++)cout<<a[i]<<";";
return 0;
}
运行结果为:
插入排序
概念
插入排序是最贴合生活的一种排序方式,比如总共有n个人需要按身高从高到低排序,按照插入排序的思想,其过程是这样的:
- 首先默认第一个最矮,先站在前面
- 下来是第二个人,如果第二个人比第一个人矮,就让第二个人站在第一个人的前面,然后第一个人往后移一位,站在第二个人原来的位置上,如果第二个人高,则直接站在第一个人身后
- 下来是第三个人,将第三个人的身高与依次与前面排好序的人进行比较,如果第三个人的身高小于某一个人的身高但大于他前面那个人的身高,则将第三个人插入到这个人的位置,而这个人及其以后的人往后统一移一位
- 下来是第四个人,重复3的步骤
- 直到第n个人也排好序为止。
实现
template<class T>
void insertSort(T *a,const int len){ //n表示数组的长度
T temp;
int left,right;
for(right=1;right<len;right++){
left = right;
temp = a[right];
while(left>0 && a[left-1]>temp){
a[left] = a[left-1];
left--;
}
a[left] = temp;
}
}
int main(){
int a[] = {5,4,7,6,8,0,9,1,2};
insertSort(a,9);
for(int i = 0;i<9;i++){
cout<<a[i]<<";";
}
}