sorting(按从小到大排序)
一、堆排序(选择排序)
不稳定
步骤:
大顶堆:每个节点的值都大于等于其左右子节点的值(用于升序)
小顶堆:每个节点的值都小于等于其左右子节点的值(用于排序)
1、构造初始堆
将序列构造成二叉树(按下标构造)
2、构造大顶堆
(1)从最后一个非叶子节点开始,从右向左,从下至上进行调整(找出父节点、左子节点、右子节点中最大的与父节点交换,使得父节点最大),使得堆顶元素最大
(2)将堆顶元素与末尾元素交换,这样末尾元素最大(固定此末尾元素),重复(1),找到第二大元素,循环直到排好序
c++代码:
void HeapSort(vector<int>& sequence)
{
const int c_len = sequence.size(); //待排序序列长度
int len = c_len, left, right, temp;
while(len>1)
{
for(int i=len-1; i>=0; --i)
{
right = 2 * (i+1); //右子节点的index
left = right - 1; //左子节点的index
/*****从非叶子节点开始构造大顶堆******/
if(left >= len) //表明sequence[i]是叶子节点
break;
if(right>=len)
{
if(sequence[i]<sequence[left])
{
temp = sequence[i];
sequence[i] = sequence[left];
sequence[left] = temp;
}
}
else
{
if(sequence[left] > sequence[right])
{
if(sequence[i] < sequence[left])
{
temp = sequence[i];
sequence[i] = sequence[left];
sequence[left] = temp;
}
}
else
{
if(sequence[i] < sequence[right])
{
temp = sequence[i];
sequence[i] = sequence[right];
sequence[right] = temp;
}
}
}
}
/******将堆顶元素与末尾元素交换******/
temp = sequence[0];
sequence[0] = sequence[len-1];
sequence[len-1] = temp;
/******忽略末尾元素,继续寻找剩下的元素中最大值*****/
--len;
}
}
空间复杂度:只有temp占用空间
S(n) = 1
时间复杂度:
任意情况:T(n) =θ(nlgn)