演算法題 BFPRT演算法 求第K小或者第K大的數

2021-08-11 03:28:49 字數 2255 閱讀 4353

2017/11/21

bfprt問題

乙個陣列中求第k小或者第k大的數

不通過排序求第k小的數,時間複雜度為o(n)。

1、找到乙個劃分值,按照partition的過程,分為小於區、等於區、大於區,則可知等於區是在整個陣列有序後不變的部分。

2、求第k小的數,就是陣列有序後下標為k-1的數。

3、所以,如果等於區包含這個k-1,則等於區的數就是第k小的數,直接返回。否則,繼續partition過程。

bfprt的思想是對劃分值的選擇進行優化,不再是隨機選取劃分值,而是通過這樣乙個過程:

1、將陣列分為5個一組,不足5個的自動成一組。劃分組所用時間為o(1)。

2、將每個組進行組內排序,可用插入排序。因為排序只有5個數,時間複雜度可記為o(1),所有組都排序為o(n)。

3、得到每個組內的上中位數,然後將這些上中位數組成新的陣列mediums。

4、求出mediums陣列中的上中位數pvalue,不使用排序,用的是遞迴呼叫bfprt的過程,求上中位數就是求mediums陣列第mediums.size()/2小的數。

5、此時得到的pvalue就是選取的劃分值,然後進行partition過程即可。

為什麼要這樣選取劃分值,這是因為,假設陣列長度為n,則mediums陣列的長度為n/5,則得到的pvalue在medium中會有n/10的數比其小,而這n/10的數,在自己的5個數的小組中,又會有3個數比pvalue小,所以,至少有n/10*3即3n/10個數比pvalue小,至多有7n/10個數比pvalue大,可以確定的淘汰掉3n/10的數。這樣劃分比較均衡。

6、剛才拿到pvalue劃分值之後,進行partition過程,會返回等於區的邊界下標。

7、如果k在等於的範圍內,則返回pvalue;k在等於區的左邊,則遞迴呼叫左邊小於區的部分;k在等於區的右邊,則遞迴呼叫大於區的部分。

#include 

#include

using

namespace

std;

/*2017/11/18

bfprt演算法:

乙個陣列中求第k小或者第k大的數

*/#if 1

#define max(a,b)(a>b?a:b)

#define min(a,b)(aint mink(vector

&a, int k);

int findkmin(vector

&a, int start, int end, int k);

int getmediumofmedium(vector

a, int start, int end);

vector

partition(vector

&a, int start, int end, int value);

int getmedium(vector

a, int start, int end);

void insertsort(vector

&a, int start, int end);

void myswap(int &a, int &b);

void myswap(int &a, int &b)

void insertsort(vector

&a, int start, int end)

}}int getmedium(vector

a, int start, int end)

vector

partition(vector

&a, int start, int end, int value)

vector

p;p.push_back(less + 1);

p.push_back(more - 1);

return p;

}int getmediumofmedium(vector

a, int start, int end)

return findkmin(mediums, 0, mediums.size() - 1, (mediums.size() - 1) / 2);

}int findkmin(vector

&a, int start, int end, int k)

int mink(vector

&a, int k)

void main()

; cout

<< mink(a, 4) << endl;

system("pause");

}#else

#endif

BFPRT演算法O n 解決第k小的數

第k小演算法 我們通常會簡單地進行乙個快速排序後,得到第k個位置上的數字即可。我們都知道的是快速排序是個不穩定的排序,它的排序過程簡單的理解主要是兩個概念partion,pivot 基準數 一趟快速排序的過程如下 先從序列中選取乙個數作為基準數 將比這個數大的數全部放到它的右邊,把小於或者等於它的數...

分治演算法求第k小元素

1.問題 用分治的演算法求乙個陣列s n 中第k小的元素。2.解析 採取和快速演算法相同的思路,但是結合分治的思想,選取恰當的基準值。找到基準值以後,再按照快速排序的方法進行查詢就好了。3.設計 int r 5int r group ceil high low 1 1.0 r ceil取上限,總共分...

第k個小的數 bfprt演算法與快排改進

public static intfindk int nums,int m,int n int k while i temp if i nums m nums j nums j temp if j 1 k else if j 1 k else public static void main stri...