BFPRT(Blum、Floyd、Pratt、Rivest、Tarjan)算法
https://en.wikipedia.org/wiki/Median_of_medians
最坏时间复杂度为O(n)
T(n) <= T(n/5) + T(7n/10) + an
T(n) <= cn
T(n/5) + T(7n/10) + an <= cn/5 + 7cn/10 + an = 9cn/10 + an <= cn
c >= 10a
实现
void swap(int *A,int p,int r)
{
if(p!=r)
{
A[p]^=A[r];
A[r]^=A[p];
A[p]^=A[r];
}
}
void insertionSort(int *A,int p,int r)
{
for(int j=p+1;j<=r;++j)
{
int key=A[j],i=j-1;
for(;i>=p&&A[i]>key;--i)A[i+1]=A[i];
A[i+1]=key;
}
}
int partition(int *A,int p,int r,int pivot)
{
swap(A,pivot,r);
int i=p-1;
for(int j=p;j<r;++j)
{
if(A[j]<=A[r])swap(A,++i,j);
}
swap(A,i+1,r);
return i+1;
}
int BFPRT(int *A,int p,int r,int k)
{
if(r-p+1<=5)
{
insertionSort(A,p,r);
return p+k-1;
}
int end=p-1;
for(int i=p;i+4<=r;i+=5)
{
insertionSort(A,i,i+4);
swap(A,++end,i+2);
}
int mid=BFPRT(A,p,end,(end-p+2)/2);
int q=partition(A,p,r,mid);
int cur=q-p+1;
if(cur==k)return q;
else if(cur>k) return BFPRT(A,p,q-1,k);
else return BFPRT(A,q+1,r,k-cur);
}