冒泡排序的優化

傳統的冒泡排序算法我們應該很熟悉,主要的原理是:

1.比較相鄰的元素。如果第一個比第二個大,就交換他們兩個。

2.對每一對相鄰元素作同樣的工作,從開始第一對到結尾的最後一對。在這一點,最後的元素應該會是最大的數。

3.針對所有的元素重複以上的步驟,除了最後一個。

4.持續每次對越來越少的元素重複上面的步驟,直到沒有任何一對數字需要比較。

但是此種方法每一趟循環只能找到一個最大或者最小的值,效率低,基於這個缺點,我們可以利用在每一趟排序中進行正向

和反向兩遍冒泡的方法,一次可以得到兩個值,最大值和最小值,確定兩個值的位置這樣我們的循環次數就減少了一半。

直接上代碼吧:

void bubble_sort_test(){
	
	int arr[] = { 5, 6, 8, 3, 9, 2, 7, 0, 4, 1 };
	int sz = sizeof(arr)/sizeof(arr[0]);
	for (int i = 0; i < sz/2; i++){
		//正向循環 把最大這下沉到 j+1的位置
		for (int j = i; j< sz - i - 1; j++){
			//前一個數大於後一個   下沉
			if (arr[j]>arr[j + 1]){
				int tmp = arr[j];
				arr[j] = arr[j + 1];
				arr[j + 1] = tmp;
			}
		}
		//反向循環 把最小者上冒的i的位置。
		for (int j = sz-1; j>i; j--){
			// 後一個數比前一個數小   上冒 
			if (arr[j]<arr[j - 1]){
				int tmp = arr[j];
				arr[j] = arr[j - 1];
				arr[j - 1] = tmp;
			}
		}
	}
	int i = 0;
	for (i = 0; i < sz; i++){
		printf("%d ", arr[i]);
	}
}

int main(){

	bubble_sort_test();
	getchar();
	return 0;
}

 

還有一種情況,如果給出的數組中已經有大量已經排序好的數據,那麼按照原始方法我們還是要跑n-1趟,這是挺浪費時間的。

於是可以這樣,我們每跑完一趟就判斷一次原數組是否有序,如果有序就結束。

所以就有了一個標誌位flag來助我們判斷。

首先來看看分析:

話不多說,代碼纔是硬道理:

void bubble_sort(int arr[], int sz)
{
	int i = 0;
	int j = 0;

	for (i = 0; i < sz - 1; i++)
	{
		int flag = 1;//假定每次進入都是有序的 flag爲1;
		for (j = 0; j < sz - i - 1; j++){
			int tmp = 0;
			if (arr[j] > arr[j + 1]){
				tmp = arr[j];
				arr[j] = arr[j + 1];
				arr[j + 1] = tmp;
				flag = 0;//如果發生交換,則flag 置爲0;
			}
		}
		if (flag == 1)//如果這趟走完,沒有發生交換,則原數組有序;
			break;
	}
}

如果有興趣,可以將上下兩個代碼合二爲一,就是最終我能想到的優化了。

發佈了78 篇原創文章 · 獲贊 34 · 訪問量 4萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章