选择排序
思路:每一轮比较过程中,确定一个标准位,将待排序序列中的最大值(最小值)选出来,与标准位元素进行交换。
注意:标准位的选择,要么从开头开始向后逐位选择;要么从后向前逐位选择
结论:
-
在每一轮排序的过程中,标准位下标是不发生改变的。我们使用另一个变量遍历待排序序列,找到最小值
-
在对待排序序列进行扫描的时候,每次遇见array[j] < array[i]的情况,就及时进行交换
-
我们一般可以使用比较的轮次来表示本轮标准位的下标取值,例如第0轮,标准为下标为0,第1轮,标准位下标为1
-
如果有n个元素参与排序,则最多进行n-1轮排序即可
-
用来扫描待排序序列的下标,
从后向前走
比从前向后走
,整体排序效率更高(注意上面的动态图是从前往后走的
)
代码实现:
public void sort1(int[] array){
int tmp;
for(int i = 0;i < array.length-1;i++){
//j从后往前走
for (int j = array.length-1 ; j > i ; j--){
//如果array[j] < array[i]则交换值,将小的放到标准位(i)上
if (array[j] < array[i]){
tmp = array[j];
array[j] = array[i];
array[i] = tmp;
}
}
}
}
选择排序的优化
思路:
原生的选择排序当中,每一次都只能够选择出待排序序列中的最大值绘或者最小值放在标准位上。如果在序列的两端,分别定义最大标准位和最小标准位,在遍历待排序序列的过程中,既找出最大值,也找出最小值,就可以一轮排序,排出两个元素的有效位置。这样一来,选择排序的效率,理论上就变为原来的1/2。
注意:为了保证不丢下最大标准位与最小标准位上的元素,所以在优化的选择排序当中,每一轮比较的时候,最大标准位和最小标准位的下标,也算在待排序序列当中。
public void sort2(int[] array){
//待搜索范围
int start = 0;
int end = array.length-1;
//记录最大元素和最小元素的下标
int maxIndex;
int minIndex;
int tmp;
while (start < end){
//定义minIndex和maxIndex初始值(升序排序,左边最小,右边最大)
minIndex = start;
maxIndex = end;
//确定最大值和最小值的下标在什么位置,并未进行交换
for (int i = start ;i <= end; i++){
if (array[i] > array[maxIndex]){
maxIndex = i;
}
if (array[i] < array[minIndex]) {
minIndex = i;
}
}
//将最小值放在标准位上
tmp = array[start];
array[start] = array[minIndex];
array[minIndex] = tmp;
/*
特殊情况,如果最大值的位置刚好在开始位置,但是,上面将最小值放在标准位上的操作就改变了最大值的位置
最大值就被换到了minIndex位置上
*/
if (maxIndex == start){
maxIndex = minIndex;
}
//将最大值放在标准位上
tmp = array[end];
array[end] = array[maxIndex];
array[maxIndex] = tmp;
start++;
end--;
}
}