冒泡排序
核心思想在于“每次比较两个相邻的元素,如果它们顺序错误就把它们交换过来”,那什么是所谓顺序错误呢?
比如,我们想要进行从大到小的排序,则把小的数字往后靠
比如有五个数字12 35 99 18 76 ,我们试图将它们从大到小排序
1.我们首先比较第一12和第二35,显然35大。依据核心思想,替换二者。那么现在五个数的顺序就是: 35 12 99 18 76
2.接着我们去比较现在的第二位12和第三位99,显然12又是更小的那个数,现在顺序变为35 99 12 18 76
3.重复上面的步骤直到比较完最后一位数字,最后我们得到的顺序是35 99 18 76 12,我们可以发现,“一趟”下来之后,我们将最小的数字排序到了最后面,看到这"冒泡"的说法已经被体现出来了。
4.重复上述步骤,依次找到“第二小的”,“第三小的”…最终完成我们的排序。冒泡排序,每一趟只可以确定将一个数归位
总结:有n个数字进行排序,只需要将n-1个数归位,进行n-1趟操作
代码示例
int a[100] ;
int i,j,t,n ;
//输入一个数n,表示下面有n个数字
scanf("%d",&n);
for(i = 1 ; i <= n ; i++){
//循环读入n个数到我们的数组a中
scanf("%d",&a[i]);
//实际上,n是要小于101的(因为前面把数组大小定为了100)
}
//!下面就是冒泡排序的核心算法了
for(i = 1 ; i <= n-1 ; i++){
for(j =1 ; j <= n-1 ; j++){
//从第一位一直直到最后一位“还没归位”的数字
if(a[j] < a[j+1]){
t = a[j];
a[j] = a [j+1];
a[j+1] = t ;
//比较大小并交换,交换过程中t只是一个工具罢了
}
}
}
//这样就完成了冒泡排序了
//下面输出试试
for(i = 1 ; i<= n ;i++){
printf("%d",a[i]);
}
上述代码中,在循环里。i代表的是我们要执行的冒泡的最大次数,如前文所说n个数字的排序,我们进行n-1趟冒泡,而j则是进行每一轮的遍历搜索
实质上这个过程还可以被优化,比如说检查是否已经排序完成,检查每轮每趟的任务是否不用进行等等。这样的优化虽然不会降低复杂度,但会在一下情况下节约时间、提高效率
这里我们只是介绍冒泡,就不再细说了