一、冒泡排序
原理解析:(以從小到大排序為例)在一排數字中,將第一個與第二個比較大小,如果后面的數比前面的小,則交換他們的位置。
然后比較第二、第三個……直到比較第n-1個和第n個,此時,每一次比較都將較大的一個數往后移動,所以第n個數是所有數中最大的一個。
之后再重復以上過程,直到將所有數據按從小到大順序排列好。
編程實現:通過兩個嵌套的循環實現。外層循環執行一次,內層循環執行一遍。
其中,內層循環控制比較時的下標,外層循環控制比較的總次數。
注意:
1、每多排好一個數,可以將內層循環次數減少一次,從而程序運行提高效率。
2、總共只需為n-1個數排序,剩下的一個為最小值,不需再排序。
對於從大到小排序是同樣的原理。
代碼:
#include <stdio.h>
int main()
{
/* 定義一個未序一維數組 */
int a[10] = { 1,2,3,6,5,4,7,0,8,-3};
/* 外層循環 控制比較“趟數”,每一趟排好一個數 */
for( int i = 9; i > 0; i-- )
{
/* 內存循環 控制冒泡“次數”,每次向后冒泡 */
/* 次數受外層循環控制,每趟少冒泡一次*/
for (int j =0; j<i; j++)
{
/* 當前元素為a[j] 如果當前元素大於下一個元素a[j+1],交換值 */
if (a[j] > a[j+1] )
{
/* 使用位運算 不通過第三方變量交換兩個變量的值 */
a[j] = a[j]^a[j+1];
a[j+1] = a[j]^a[j+1];
a[j] = a[j]^a[j+1];
}
}
}
/* 遍歷輸出已序數組 */
for (int i = 0; i < 10; i++)
printf("%d ",a[i]);
return 0;
}
二、選擇排序
選擇排序可以看做是冒泡排序的優化。在選擇排序中,內層循環只負責尋找最大值的下標並保存,不需要頻繁交換值。
原理解析:1、在n個數中,先找到最大的數並記錄其下標,然后將這個數與第n個數交換值,如果剛好第n個數是最大數則不用交換。
2、重復第一步,直到所有數排好順序
編程實現:兩層循環嵌套,內循環尋找最大值的下標。
注意:選擇最大值可以假定第0個元素是最大的,碰到比他大的值就更新 int maxIndex;
每次循環之前,maxIndex必須歸0。
代碼:
#include <stdio.h>
void main()
{
int a[10] = { 5, 1, 6, 9, -8, 3, 4, 6, 10, 7 };
int maxindex = 0 , temp;
for (int j = 9; j > 0; j--)
{
maxindex = 0;
for (int i = 1; i <= j; i++)
{
if (a[maxindex] < a[i])
{
maxindex = i;
}
}
if (maxindex != j)
{
temp = a[maxindex];
a[maxindex] = a[j];
a[j] = temp;
}
}
for (int i = 0; i<10; i++)
printf("%d ", a[i]);
}
三、插入排序
原理解析:將元素插入到已序數組中的相應位置,未排序數組將第一個元素視為已序數組。
代碼實現:將第一個元素視為已序數列,按排序規則選擇位置插入。兩層循環嵌套,內層循環控制比較的次數。
代碼:
#include <iostream>
using namespace std;
int main()
{
int temp = 0;
int a[10] = { 0 };
cout << "請輸入十個數:" << endl;
for (int i = 0; i < 10; i++)
cin >> a[i];
// for循環,進行9次循環;
for (int i = 1; i < 10; i++)
// for循環,在每次大的循環中,a[i]從a[1]依次與它前面的數比較;
for (int j = i - 1; j >= 0; j--)
//如果a[j + 1]>a[j],則把這兩個數組元素互換,目的把最大的數放到前邊;
if (a[j + 1] > a[j])
{
temp = a[j + 1];
a[j + 1] = a[j];
a[j] = temp;
}else
break;
//輸出排好順序的十個數;
for (int i = 0; i < 10; i++)
cout << a[i] << " ";
return 0;
}
