返回

冒泡排序算法(10)

发布时间:2022-11-19 06:01:29 308
# 数据

关于冒泡排序算法

题目要求:

给定一组数据[10 9 8 7 6 5 4 3 2 1],利用冒泡排序法,对这组数进行升序排列。

基本思想:

依次比较两个相邻的元素,如果顺序不符合要求,就交换位置。

走访元素的工作是重复地进行直到没有相邻元素需要交换,也就是说该元素列已经排序完成。

分析

每一趟冒泡排序思想:依次比较相邻的元素,若前者大于后者要求,则交换位置。

第1趟冒泡排序:

[10 9 8 7 6 5 4 3 2 1]--->[9 10 8 7 6 5 4 3 2 1]--->[9 8 10 7 6 5 4 3 2 1]

         比较[10 9]                    交换[10  9]位置,比较[10 8]            交换[10  8]位置,比较[10 7] 

---->[9 8 7 10 6 5 4 3 2 1]--->[9 8 7 6 10 5 4 3 2 1]--->[9 8 7 6 5 10 4 3 2 1]

交换[10 7]位置,比较[10 6]    交换[10  6]位置,比较[10 5]            交换[10  5]位置,比较[10 4] 

---->[9 8 7 6 5 4 10 3 2 1]--->[9 8 7 6 5 4 3 10 2 1]--->[9 8 7 6 5 4 3 2 10 1]

交换[10 4]位置,比较[10 3]      交换[10  3]位置,比较[10 2]           交换[10  2]位置,比较[10 1] 

---->[9 8 7 6 5 4 3 2 1 10]

交换[10  1]位置,一趟冒泡排序结束

第2趟冒泡排序:(重复上面步骤)

[[9 8 7 6 5 4 3 2 1] 10]--->...--->[[8 7 6 5 4 3 2 1 9] 10]

   ...

第9趟冒泡排序:(重复上面步骤)

[[9 8 7 6 5 4 3 2 1] 10]--->...--->[[[[[[[[[[1 ]2 ]3 ]4 ]5 ]6]7 ]8] 9] 10]

到此,冒泡排序结束。

:上面有10个元素,总共经历了9趟冒泡排序。

:关于每一趟冒泡排序时的相邻元素比较次数情况如下:

          第1趟冒泡排序[10 9 8 7 6 5 4 3 2 1]时,比较相邻元素的次数共有9次;

    第2趟冒泡排序[9 8 7 6 5 4 3 2 1]时,比较相邻元素的次数共有8次;

                     ...

                 第8趟冒泡排序[3 2 1]时,比较相邻元素的次数共有2次;

    第9趟冒泡排序[2 1]时,比较相邻元素的次数共有1次;

冒泡排序函数的错误设计

#include
void bubble_sort(int arr[]){
//确定冒泡排序的趟数sz-1
int i=0;
int sz=sizeof(arr)/sizeof(arr[0]);
for(i=0;i<sz-1;i++){
//每一趟冒泡排序
int j=0;
for(j=0;j<sz-1-i;j++){
if(arr[j]>arr[j+1]){
int tmp;
tmp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=tmp;
}
}
}
}

int main(){
int arr[]={10,9,8,7,6,5,4,3,2,1};
int i=0;
int sz=sizeof(arr)/sizeof(arr[0]);
//对arr进行冒泡排序,升序处理
//arr是数组,对数组arr进行传参时,实际上传递过去的是数组arr首元素的地址&arr[0]
bubble_sort(arr);//冒泡排序
for(i=0;i<sz;i++){
printf("%d ",arr[i]);
}
return 0;
}

运行结果:

10 9 8 7 6 5 4 3 2 1
--------------------------------
Process exited with return value 0
Press any key to continue . . .

从运行结果可知:其与升序要求相悖

分析原因:arr是数组,对数组arr进行传参时,实际上传递过去的是数组arr首元素的地址&arr[0]

:对于数组,数组名是数组首元素的地址。

:但也存在数组名不是首元素的地址的情况:如下两种

i:  sizeof(数组名),指用来计算整个数组的大小(单位:字节byte);

    sizeof()内部单独放一个数组名,数组名表示的是整个数组。如:sizeof(arr)

ii:&数组名,指取出的是整个数组的地址。如:&arr

除此之外,所有的数组名都表示数组首元素的地址。

冒泡排序函数的正确设计

#include
void bubble_sort(int arr[],int sz){
//确定冒泡排序的趟数sz-1
int i=0;
for(i=0;i<sz-1;i++){
//每一趟冒泡排序
int j=0;
for(j=0;j<sz-1-i;j++){
if(arr[j]>arr[j+1]){
int tmp;
tmp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=tmp;
}
}
}
}

int main(){
int arr[]={10,9,8,7,6,5,4,3,2,1};
int i=0;
int sz=sizeof(arr)/sizeof(arr[0]);
//对arr进行冒泡排序,升序处理
//arr是数组,对数组arr进行传参时,实际上传递过去的是数组arr首元素的地址&arr[0]
bubble_sort(arr,sz);//冒泡排序
for(i=0;i<sz;i++){
printf("%d ",arr[i]);
}
return 0;
}

运行结果:

1 2 3 4 5 6 7 8 9 10
--------------------------------
Process exited with return value 0
Press any key to continue . . .

冒泡排序函数的改进设计

在处理一个有序地数组[1 2 3 4 5 67 8 9 10]或[10 1 2 3 4 5 67 8 9]时,为了提高代码效率,如何进行优化?

冒泡排序函数中定义一个变量flag,来判断数据是否为有序数列,若不是,则结束冒泡排序函数;反之亦然。

#include
void bubble_sort(int arr[],int sz){
//确定冒泡排序的趟数sz-1
int i=0;
for(i=0;i<sz-1;i++){
int flag=1;//假设这一趟要排序的数据已经有序
//每一趟冒泡排序
int j=0;
for(j=0;j<sz-1-i;j++){
if(arr[j]>arr[j+1]){
int tmp;
tmp=arr[j];
arr[j]=arr[j+1];
arr[j+1]=tmp;
flag=0;
}
}
if(flag == 1){
break;//作用于跳出外部for()循环
}
}
}

int main(){
int arr[]={10,9,8,7,6,5,4,3,2,1};
int i=0;
int sz=sizeof(arr)/sizeof(arr[0]);
//对arr进行冒泡排序,升序处理
//arr是数组,对数组arr进行传参时,实际上传递过去的是数组arr首元素的地址&arr[0]
bubble_sort(arr,sz);//冒泡排序
for(i=0;i<sz;i++){
printf("%d ",arr[i]);
}
return 0;
}

:break语句只适用于for()和swifch中,在if()语句中不能使用,因为if()不是循环语句,不能用break来结束。

arr和&arr{0}等价,都是首个元素的地址;

&arr表示整个素组的地址。

----------END----------



特别声明:以上内容(图片及文字)均为互联网收集或者用户上传发布,本站仅提供信息存储服务!如有侵权或有涉及法律问题请联系我们。
举报
评论区(0)
按点赞数排序
用户头像
精选文章
thumb 中国研究员首次曝光美国国安局顶级后门—“方程式组织”
thumb 俄乌线上战争,网络攻击弥漫着数字硝烟
thumb 从网络安全角度了解俄罗斯入侵乌克兰的相关事件时间线
下一篇
三子棋游戏 2022-11-19 05:52:29