1.基础知识
在学排序之前要先了解2个简单的算法
- 交换数组的2个位置的元素
void swap(int a[],int x,int y){//x和y是数组要要换位置的元素
int temp=a[x];
a[x]=a[y];
a[y]=temp;
}
- 找出数组的最大(最小)元素的位置
int maxIndex(int a[],int n){
int k=0;//k用来标记数组最大元素的下标
for (int i=1;i<n;i++){//从数组第二个元素比较
if(a[i]>a[k]){k=i;}
}
return k;
}
2.排序的引入
在数组a中有 5,2,8,4,6,1,3,7,9,0共10个元素,我们如何将其从小到大排序呢?
方法一:选择排序
第一次在数组中选出最小的元素和a[0]交换
第二次在数组其他n-1个元素中选出最小的元素和a[1]交换
第三次在数组其他n-2个元素中选出最小的元素和a[2]交换
。。。。。。
一直循环下去,最终可以得到结果
上述的过程为:
开始:5,2,8,4,6,1,3,7,9,0
第一次:0,2,8,4,6,1,3,7,9,5
第二次:0,1,8,4,6,2,3,7,9,5
第三次 :0,1,2,4,6,8,3,7,9,5
第四次:。。。。
第十次:。。。。
事实上当第9次时,第9个位置选择好了,第十个位置自然也就选择好了
代码如下:
下面所有代码中默认知道数组长度为10,不知道时可以定义数组长度为len;函数形参列表中加入数组长度参数
void selectSort(int a[]){
for(int i=0;i<10;i++){//这里多了一趟,9趟操作就够了
int k=i;
//找最小元素的下标
for(int j=i;j<10;j++){
if(a[j]<a[k]) k=j;
}
//找到这次的最小元素的下标,进行交换
int temp=a[i];
a[i]=a[k];
a[k]=temp;
}
}
方法二:冒泡排序
重复地走访过要排序的元素列,依次比较两个相邻的元素,如果前面一个比后面一个大,则这两个位置发生交换。
按这种交换方法,每次确定出一个最大的元素位于数组的最后一个位置
给人一种最大(最小)的元素一直往后冒的感觉,形象的称为冒泡排序。
例如:
开始时:5,2,8,4,6,1,3,7,9,0
第一趟:a[0]~a[n-1]
5 2交换: 2,5,8,4,6,1,3,7,9,0
8 4交换: 2,5,4,8,6,1,3,7,9,0
8 6交换: 2,5,4,6,8,1,3,7,9,0
8 1交换: 2,5,4,6,1,8,3,7,9,0
8 3交换: 2,5,4,6,1,3,8,7,9,0
8 7交换: 2,5,4,6,1,3,7,8,9,0
9 0交换: 2,5,4,6,1,3,8,7,0,9
至此,第一趟交换完成 a[n-1]的位置元素确定;
第二趟:a[0]~a[n-1-1]
。。。。
。。。。
事实上共计n-1趟就可以完成排序
代码如下:
void bubbleSort(int a[]){
int temp=0;
for(int i=0;i<9;i++){
for(int j=0;j<10-i-1;j++){
if(a[j]>a[j+1]){
temp=a[j];
a[j]=a[j+1];
a[j+1]=temp;
}
}
}
}
冒泡排序的改进
在排序过程中,如果在某一趟中,均没有发生交换,说明此事排序完成,没有必要再进行下一趟,由此我们可以增加一个标志变量falg来标志该趟是否发生交换。
void bubbleSort(int a[]){
bool flag=true; //设置标记变量
int temp=0;
while(flag){
flag=false;
for(int i=0;i<9;i++){
for(int j=0;j<10-i-1;j++){
if(a[j]>a[j+1]){
temp=a[j];
a[j]=a[j+1];
a[j+1]=temp;
flag=true;
}
}
}
}
}
方法三:插入排序
插入排序理解最为简单,对于数组中的元素5,2,8,4,6,1,3,7,9,0
开始时:5
第一次插入:2,5
第二次插入:2,5,8
第三次插入:2,4,5,8
第四次插入:2,4,5,6,8
…
第九次插入:。。。
实现代码:
void insertSort(int a[]){
for(int i=1;i<10;i++){
int j=i;int temp=a[i];//找插入位置
while(j!=0&&temp<a[j-1]){
a[j]=a[j-1];//向后移动
j--;
}
a[j]=temp;// 插入
}
}
插入排序思想容易理解,代码实现比较难懂,应多多体会,走一遍代码更方便理解。