
OrderStatistics 排位统计:集合中第i小的元素
中位数:快排中找中位数,代价大
寻找集合中第i小的元素:

我们可以多快解决这个问题?
下面尝试用O(n)解决
算法思路:
利用带有随机的partition算法确定pivot的位置,按照pivot位置和要找的元素的排名对对应的部分进行递归
终止条件:区间长度为1或者是pivot位置就是rank位置
递归找左还是右不要搞错
算法实现:
int randomizedSelect(vector<int>& vec, int start, int end, int rank) {
if (start == end) return vec[start];
int pivot_index = randomizedPartition(vec, start, end);
int pivot_rank = pivot_index - start + 1;
if (pivot_rank == rank) {
return vec[pivot_index];
}
if (rank < pivot_rank) {
return randomizedSelect(vec, start, pivot_index - 1, rank); // 左边找
}else{
return randomizedSelect(vec, pivot_index + 1, end, rank - pivot_rank); // 右边找
}
}
最坏情况下时间复杂度: T ( n ) = T ( n − 1 ) + Θ ( n ) = Θ ( n 2 ) T(n) = T(n-1) +\Theta(n) = \Theta(n^2) T(n)=T(n−1)+Θ(n)=Θ(n2)
与快排区别,快排是两个子问题。
对于快排的时间复杂度,若找中值是线性开销,那么:
T
(
n
)
=
2
T
(
n
/
2
)
+
O
(
n
)
+
O
(
n
)
=
Θ
(
n
l
g
n
)
T(n) = 2T(n/2) + O(n) + O(n) =\Theta(nlgn)
T(n)=2T(n/2)+O(n)+O(n)=Θ(nlgn)
若找中值是最坏情况:
T
(
n
)
=
2
T
(
n
/
2
)
+
O
(
n
)
+
O
(
n
2
)
T(n) = 2T(n/2) + O(n) +O(n^2)
T(n)=2T(n/2)+O(n)+O(n2)
线性的找中值:

每5个一组,快速通过直接插入排序找到中值,每组中值的中值作为pivot。
T
(
n
)
=
T
(
n
/
5
)
+
Θ
(
n
)
+
T
(
7
n
/
10
)
=
Θ
(
n
)
T(n) = T(n/5) + \Theta(n) + T(7n/10) = \Theta(n)
T(n)=T(n/5)+Θ(n)+T(7n/10)=Θ(n)