輕鬆掌握快速排序

 

目錄

 

一、概述

二、快速排序實現

1、雙指針法實現分割數組

2、quicksort實現

3、quick sort調用

三、總結


一、概述

快速排序使用分治法(Divide and conquer)策略來把一個序列(list)分爲較小和較大的2個子序列,然後遞歸地排序兩個子序列。

步驟爲:

  1. 挑選基準值:從數列中挑出一個元素,稱爲“基準”(pivot),
  2. 分割:重新排序數列,所有比基準值小的元素擺放在基準前面,所有比基準值大的元素擺在基準後面(與基準值相等的數可以到任何一邊)。在這個分割結束之後,對基準值的排序就已經完成,
  3. 遞歸排序子序列:遞歸地將小於基準值元素的子序列和大於基準值元素的子序列排序。

遞歸到最底部的判斷條件是數列的大小是零或一,此時該數列顯然已經有序。

選取基準值有數種具體方法,此選取方法對排序的時間性能有決定性影響。

二、快速排序實現

1、雙指針法實現分割數組

這個雙指針法實現分割數組可以解決很多問題,其中有個移0問題(把數組中所有的0都移到後面)也可以用這個方法解決。

int partionArray(std::vector<int> &vecNums, int left, int right,int pvIndex)
{

	int pvval = vecNums[pvIndex];//保存基準值
	std::swap(vecNums[pvIndex], vecNums[right]);//基準值換到最後
	int storeIndex = left;//指向最後一個滿足<= pvval索引的下一個位置,雙指針中一個指針
	for (int i = left; i < right; ++i)//i爲雙指針的第二個指針
	{
		if (vecNums[i] <= pvval)
		{
			std::swap(vecNums[i], vecNums[storeIndex]);
			storeIndex++;
		}
	}

	std::swap(vecNums[storeIndex], vecNums[right]);
	return storeIndex;
}

2、quicksort實現

有了這個partionArray,quicksort就比較容易寫出來了。

void quicksort(std::vector<int> &vecNums, int left, int right)
{
	if (right > left)
	{
		int pvIndex = rand()%(right-left+1) +left;//隨機選擇基準值
		int parIndex = partionArray(vecNums, left, right, pvIndex);
    	quicksort(vecNums, left, parIndex - 1);
		quicksort(vecNums, parIndex + 1, right);

	}
}

3、quick sort調用

int main()
{	
    std::vector<int> vecNums = { 2,4,9,1 };
	quicksort(vecNums, 0, vecNums.size() - 1);

	return 0;
}

 

三、總結

    這裏的關鍵是partionArray的雙指針方法,大家可以重點掌握,這個方法可以用來解決一系列的問題。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章