堆排序原理和實現

參考文獻

1.堆排序原理
2.堆排序的手寫實現


在這裏插入圖片描述
在這裏插入圖片描述

堆排序思想

Step 1: 構造初始堆
初始化堆時是對所有的非葉子結點進行篩選;
最後一個非終端元素的下標是[n/2]向下取整,所以篩選只需要從第[n/2]向下取整個元素開始,從後往前進行調整。

Step 2:進行堆排序
堆排序是一種選擇排序。建立的初始堆爲初始的無序區。
排序開始,首先輸出堆頂元素(因爲它是最值),將堆頂元素和最後一個元素交換,這樣,第n個位置(即最後一個位置)作爲有序區,前n-1個位置仍是無序區,對無序區進行調整,得到堆之後,再交換堆頂和最後一個元素,這樣有序區長度變爲2。
不斷進行此操作,將剩下的元素重新調整爲堆,然後輸出堆頂元素到有序區。每次交換都導致無序區-1,有序區+1。不斷重複此過程直到有序區長度增長爲n-1,排序完成。

時間複雜度:O(nlogn)


手寫堆排序

void HeapCore(vector<int> &vec ,int size, int end)
{
	int i = end;
	int j = i;
	bool flag = false;
	do{
		flag = false;
		if(i * 2 < size && vec[i] > vec[i *2])
			j = i*2;
 
		if(i *2 + 1 < size && vec[i*2 + 1] < vec[i*2] && vec[i] > vec[i *2] ) 
			j = i*2 + 1;

		if(i != j)
		{
			int tmp = vec[j];
			vec[j] = vec[i];
			vec[i] = tmp;
			flag = true;
		}
		i = j;
	}while(flag && i < size);
}

void Heap(vector<int >&vec)
{
	for(int i = (vec.size() - 1)/2 ; i > 0 ; i--)
		HeapCore(vec , vec.size() ,i);
	
	for(int i = vec.size() - 1; i > 0 ; i--)        // 將第一個個與最後一個交換
	{
			int tmp = vec[1];
			vec[1] = vec[i];
			vec[i] = tmp;
			if(i > 1)
			HeapCore(vec , i , 1);
	}
}

int main()
{ 
	vector<int > vec;
	for(int i = 0 ; i < 100 ; i++)
		vec.push_back(i);
	Heap(vec);
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章