您的位置:首页 > 其它

选择排序和冒泡排序区别以及冒泡排序优化

2015-12-07 22:58 597 查看
简单选择排序和冒泡排序区别

我一直搞不太清这两个具体区别。打算研究下。

我认为两种主要区别是(有不同意见请告知):冒泡每次循环都是相邻两数的比较(内层循环都是j和j+1比较),选择排序是某一下标元素与其他下标元素依次比较(内层循环是i和j的比较)。

一、冒泡排序

依次对相邻两数作比较,若前面的大于后面的,则交换。

第一次循环后,最大的数已经出现在最后的。

第二次循环后,第二大的数在倒数第二的位置上。

依此循环,知道数组有序。排序过程如下:



public static void sort(int[] a){
int len = a.length;
for(int i = 0; i< len; i++){        //控制循环的次数。
for(int j = 0; j<len-i-1;j++){    //控制比较数的下标。
if(a[j]>a[j+1]){
swap(a, j, j+1);
}

System.out.print("i = " +i+", j = "+j+"    ");
print(a);
}
}
}

private static void swap(int[]a, int i, int j ){
int temp = a[i];
a[i] = a[j];
a[j]= temp;
}

优化1:控制外层循环的次数

对上述冒泡方法可以进行优化,就是定义个标记,来辅助控制外层循环的次数。

/**
* 使用标志位来控制外层循环的次数
* @param a
*/
public static void sort1(int[] a){
int len = a.length;
boolean flag = true;    //控制外层循环次数,若数组已经有序了,就不比较了。
for(int i = 0; i< len; i++){    
flag = true;
for(int j = 0; j<len-i-1;j++){    
if(a[j]>a[j+1]){
flag = false;
swap(a, j, j+1);
}
}
if(flag){
break;
}
}
}

优化2:在上面进一步,控制内外层循环的次数。

第二种方法是参考此文。


/**
* 记录上次交换的位置,以此为内层循环的界限。
* @param a
*/
public static void sort2(int[] a){
int len = a.length;
boolean flag = true;    //控制外层循环次数,若数组已经有序了,就不比较了。
int lasttemp = len-1;
for(int i = 0; i< len; i++){    
flag = true;
int last = lasttemp;
for(int j = 0; j<last;j++){    
if(a[j]>a[j+1]){
flag = false;
swap(a, j, j+1);
lasttemp =j;  //记录最后以此交换的位置。此位置之后为有序的。
}
}
if(flag){
break;
}
}
}

二、简单选择排序:

从第一个元素开始,与后续元素进行比较,若前面大于后面的,则交换;依此循环。

public static void selectSort(int[]a){
int len = a.length;
for(int i = 0; i<len;i++){
for(int j = i+1;j<len;j++){
if(a[i]>a[j]){
swap(a, i, j);
}
System.out.print("i = " +i+", j = "+j+"    ");
print(a);
}
}
}

选择排序优化思路和冒泡不一样。冒泡能如此优化是因为每轮循环后,都能知道数组的局部排序情况,而选择不行。

选择排序可以减少交换次数,每轮循环结束后再进行交换。网上很多,这里不说了。若有更好的优化方法,请告知。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: