每次只能肯定將一個數歸位。即第一趟只能肯定將末位上的數字歸位,第二趟只能將倒數第二位的數字歸位......數組
若是有 n 個數進行排序,只需將 n-1個數歸位,也就是說要進行n-1 趟操做。 而「每一趟」都須要從第 1 位開始進行相鄰兩個數的比較,將較小的一個數放在後面,比較完畢後向後挪一位繼續比較下面兩個相鄰數的大小,重複此步驟,直到最後一個還沒有歸位的數(這個循環次數爲n-i,也就是說將已經排列好順序的i個數排除在外),已經歸位的數則無需再進行比較(若是是按照遞減順序排列,已經歸位的數字位於末尾)。spa
#include<stdio.h> int main(){ int a[100]; int i,j,n,t; scanf("%d",&n); for(int i=1;i<=n;i++){ scanf("%d",&a[i]); //將輸入暫存在數組中,桶排序是提早申請數組,按照規定位置插入 } for(i=1;i<=n-1;i++){ //n維數組只須要比較n-1趟 for(j=1;j<=n-i;j++){ //這是數組中每一個元素須要比較的次數 //由於以前已經進行過i個數的排序,所以只須要進行n-i趟便可 if(a[j]<a[j+1]){ t=a[j]; a[j]=a[j+1]; a[j+1]=t; } } } for(int i=1;i<=n;i++){ printf("%d ",a[i]); //這裏的輸出爲數組中的元素,不要寫成&a[i],這樣輸出的就是數組元素的地址了 } getchar(); getchar(); return 0; }
#include<stdio.h> struct student{ char name[21]; char score; //參考代碼給出的是char類型,這裏可使用int score }; int main(){ struct student a[100],t; int i,j,n; scanf("%d",&n); for(int i=0;i<n;i++){ scanf("%s %d",&a[i].name,&a[i].score); } for(int i=0;i<n-1;i++){ for(int j=0;j<=n-i;j++){ if(a[j].score<a[j+1].score){ t=a[j]; a[j]=a[j+1]; a[j+1]=t; } } } for(int i=0;i<n;i++){ printf("%s %d\n",a[i].name,a[i].score); //printf("%s,%d\n",a[i].name,a[i].score); //printf("%d ",a[i].score); //printf("\n"); //這是幾種不一樣的輸出方案 } getchar(); getchar(); return 0; } 深度剖析: scanf("%s %d",&a[i].name,&a[i].score); 疑問:此處寫成scanf("%s %d",a[i].name,&a[i].score);也能夠執行,緣由何在? 解析:scanf中&是取址,將輸入的值存到變量的地址內存單元,而變量是數組或者指針時就是地址不用再對變量取址!這裏name是數組,變量即爲地址,而score是int類型變量,若是去掉取址符號會出錯。
冒泡排序的時間複雜度是O(N²),這是一個很是高的時間複雜度。指針