冒泡排序法
一、冒泡排序就是不断“挪数到最后”
按照从小到大的顺序用冒泡排序法如图:
-
在数组所有数中,把数值最大的挪到最后(红色箭头位置):
-
在剩下的数中(蓝色圈里的),把数值最大的挪到最后(红色箭头位置):
-
继续在剩下的数中(蓝色圈里的),把数值最大的挪到最后(红色箭头位置):
-
然后一直重复……
-
到只剩下两个的时候即为排序的最后一次,这次完成后数组首个数值也会跟着定下来:
现在研究一下,“把数值最大的挪到最后”这个操作要执行几次:
如果数组只有1个元素,就不用排序了
如果数组有2个元素,挪数的操作需要1次
如果数组有3个元素,挪数的操作需要2次
如果数组有4个元素,挪数的操作需要3次
……
可以推出:如果数组有n个元素,挪数的操作需要n-1次。
二、如何实现“把数挪到最后”
-
如何在数组所有元素(蓝色圈里的)中,把数值最大的挪到最后(红色箭头位置)
先看数组第1个元素(数组[0]
),拿它和它后面的元素(数组[1]
)做比较:
- 如果
数组[0]
>数组[1]
,就交换它俩的数值,保证后面的元素的数值要比前面的大。 - 如果
数组[0]
<=数组[1]
,就不用管它们。
然后接着看数组第2个元素(
数组[1]
),拿它和它后面的元素(数组[2]
)做比较:
- 如果
数组[1]
>数组[2]
,就交换它俩的数值,保证后面的元素的数值要比前面的大。 - 如果
数组[1]
<=数组[2]
,就不用管它们。
再继续接着看数组第3个元素(
数组[2]
),拿它和它后面的元素(数组[3]
)做比较:
一直重复……,当看到数组倒数第二个元素时就是最后一次:
- 如果
假设这个数组有n个元素,在这一轮中,从数组第一个元素(
数组[0]
)开始看,看到数组倒数第二个元素,总共看了n-1个元素
- 如何在数组剩下的数(蓝色圈里的)中,把数值最大的挪到最后(红色箭头位置):
先看数组第1个元素(数组[0]
),拿它和它后面的元素(数组[1]
)做比较;
然后接着看数组第2个元素(数组[1]
),拿它和它后面的元素(数组[2]
)做比较;
再继续接着看数组第3个元素(数组[2]
),拿它和它后面的元素(数组[3]
)做比较;
一直重复……,当看到蓝色圈里的倒数第二个元素时就是最后一次:
这一轮中,从数组第一个元素(
数组[0]
)开始看,看到数组倒数第三个元素,总共看了n-2个元素
- 用上述方法继续确定数组倒数第三元素的值、倒数第四元素的值、……
- 一直到数组第二元素的值被确定下来,整个冒泡排序法就完成了。
三、小例子
用冒泡排序法对数组int data[]={12,8,13,9}
排序(从小到大)
#include <stdio.h>
int main(void)
{
int data[] = {12,8,13,9};
int ArrayLength = sizeof(data)/sizeof(data[0]);//求数组长度(数组有多少个元素)
int temp;
for(int i=0; i<ArrayLength-1; i++)
{
for(int j=0; j<ArrayLength-1-i; j++)
{
if(data[j] > data[j+1])
{
temp = data[j];
data[j] = data[j+1];
data[j+1] = temp;
}
}
}
for(int i=0; i<ArrayLength; i++)
{
printf("%d ",data[i]);
}
return 0;
}
-
i
=0:-
j
=0,看data[0]
,拿它和它后面的元素data[1]
比较12>8,互换它俩的位置,此时数组data的顺序为:8、12、13、9
-
j
=1,看data[1]
,拿它和它后面的元素data[2]
比较12<13,不用管它俩,此时数组data的顺序为:8、12、13、9
-
j
=2,看data[1]
,拿它和它后面的元素data[2]
比较13>9,互换它俩的位置,此时数组data的顺序为:8、12、9、13
-
-
i
=1:-
j
=0,看data[0]
,拿它和它后面的元素data[1]
比较8<12,不用管它俩,此时数组data的顺序为:8、12、9、13
-
j
=1,看data[1]
,拿它和它后面的元素data[2]
比较12>9,互换它俩的位置,此时数组data的顺序为:8、9、12、13
-
-
i
=2:-
j
=0,看data[0]
,拿它和它后面的元素data[1]
比较8<9,不用管它俩,此时数组data的书序为:8、9、12、13
-
用表格的形式来看,从小到大用冒泡排序法对数组int data[]={12,8,13,9}
排序:
j=0 | j=1 | j=2 | ||
---|---|---|---|---|
i=0 | 8、12、13、9 | 8、12、13、9 | 8、12、9、13 | 最后一个元素值最大确定为13 |
i=1 | 8、12、9 | 8、9、12 | 倒数第二个元素值最大确定为12 | |
i=2 | 8、9 | 倒数第三个元素值最大确定为9 |
简单选择排序法
一、选择排序就是不断“找数比较”
按照从小到大的顺序用冒泡排序法如图:
-
看数组第一个元素,拿它的数值和数组其它元素的数值(蓝色圈里的)做比较,如果发现有比它大的,就交换它俩的数值,确保第一个元素的值在所有元素中是最小的
-
看数组第二个元素,拿它的数值和数组其它元素的数值(蓝色圈里的)做比较,如果发现有比它大的,就交换它俩的数值,确保第二个元素的值比蓝色圈里的都要小
-
看数组第三个元素,拿它的数值和数组其它元素的数值(蓝色圈里的)做比较,如果发现有比它大的,就交换它俩的数值,确保第三个元素的值比蓝色圈里的都要小
-
然后一直重复……
-
最后一次是用数组倒数第二个元素和倒数第一个元素做比较,比较完这次后就结束
如果数组有只有1个元素,就不用排序了
如果数组有2个元素,就需要看数组第一个元素,总共1次
如果数组有3个元素,就需要看数组第一、二个元素,总共2次
如果数组有4个元素,就需要看数组第一、二、三个元素,总共3次
……
可以推出:如果数组有n个元素,就需要看数组第一、二、三、……n-1个元素,总共n-1次
二、如何“比较”
-
看数组第一个元素
数组[0]
,如何拿它的数值和数组其它元素的数值(蓝色圈里的)做比较,以确保它的值在所有元素中是最小的
先拿数组第二个元素数组[1]
和数组第一个元素数组[0]
作比较
- 如果
数组[0]
>数组[1]
,就交换它俩的数值,保证数组[0]
的数值是最小的。 - 如果
数组[0]
<=数组[1]
,就不用管它们。
再拿数组第三个元素
数组[2]
和数组第一个元素数组[0]
作比较
- 如果
数组[0]
>数组[2]
,就交换它俩的数值,保证数组[0]
的数值是最小的 - 如果
数组[0]
<=数组[2]
,就不用管它们
一直拿数组第四个、第五个、……到数组最后一个元素,来和数组第一个元素
数组[0]
作比较
比较完就能保证数组第一个元素数组[0]
的值是最小的。 - 如果
-
继续看数组第二个元素
数组[1]
,从数组第三个元素数组[2]
开始和它做比较
- 如果
数组[1]
>数组[2]
,就交换它俩的数值 - 如果
数组[1]
<=数组[2]
,就不用管它们
然后拿数组第四个、第五个、……到数组最后一个元素,来和数组第二个元素
数组[1]
作比较
- 如果
-
用上述方法一直确定数组第三个元素、第四个元素……
-
一直到确定完数组倒数第二个元素,整个简单选择排序法就完成了
三、小例子
用选择排序法对数组int data[]={12,8,13,9}
排序(从小到大)
#include <stdio.h>
int main(void)
{
int data[] = {12,8,13,9};
int ArrayLength = sizeof(data)/sizeof(data[0]);
int temp;
for(int i=0; i<ArrayLength-1; i++)
{
for(int j=i+1; j<ArrayLength; j++)
{
if(data[i] > data[j])
{
temp = data[i];
data[i] = data[j];
data[j] = temp;
}
}
}
for(int i=0; i<ArrayLength; i++)
{
printf("%d ",data[i]);
}
return 0;
}