为什么堆排序的空间复杂性是O(1)?
我不明白堆排序的空间复杂度是如何O(1)? 尽管快速排序不使用任何额外的数组(即就地),但在最坏的情况下其空间复杂度为O(n),最佳情况下为O(lg n),因为堆栈在后端用于递归调用。 我对吗?
堆排序也是一样。 虽然它在原地,但是由于Build-Heap函数调用Max-Heapify函数,所以它的空间复杂度应该等于Max-Heapify,即O(lg n)。 不是吗? 此外,Max-Heapify函数稍后将在根节点调用n次,正如我所说Max-Heapify()空间复杂度为O(lg n)。
所以,堆排序的整体空间复杂度应该是O(lg n)。 但是我发现它在维基百科上是O(1)。 帮助我理解它。
Heapsort不会占用任何依赖于被排序数组大小的空间,只是数组本身的空间以及一些变量。 显然O(1)。
Quicksort跟踪一堆需要排序的子数组。 如果你聪明并且任何两个子数组都将较大的那个放在堆栈上,并立即对较小的那个进行排序,则需要O(log n)。
在实践中,它没有任何区别。
空间复杂度是指算法使用的额外空间。 堆排序不使用任何额外的空间(在O(n)),除了要排序的数组。 因此它是O(1)
有heapify的非递归版本(请参阅下面的示例)。 对于快速排序,如果仅在较小的分区上使用递归,然后循环返回以将什么是较大的分区拆分为2(再次使用这些2个分区中较小的那个上的递归等),则最大堆栈空间为O(log( n)),但最坏的情况下仍然是O(n ^ 2)。
非递归heapify的非递归堆排序的C ++示例:
typedef unsigned int uint32_t;
void HeapSort(uint32_t *, size_t);
void Heapify(uint32_t *, size_t);
void SiftDown(uint32_t *, size_t, size_t);
void HeapSort(uint32_t * a, size_t count)
{
size_t end;
Heapify(a, count); // create initial heap
end = count-1;
while(end > 0){
// swap root (largest value) with end
std::swap(a[0], a[end]);
// reduce size of heap and
// increase size of sorted array
end--;
// repair the reduced heap
SiftDown(a, 0, end);
}
}
// create initial heap: for root = (count-2)/2 -> 0
// parent = root, children = root*2+1, root*2+2
// swap so that all a[parent] > a[child]
void Heapify(uint32_t * a, size_t count)
{
size_t root;
if(count < 2)
return;
// create sub-heaps of increasing size,
// with root going from (count-2)/2 to 0
root = (count - 2) / 2;
while(1){
SiftDown(a, root, count-1);
if(root == 0)
break;
root--;
}
}
// scan from root to end, swapping as needed to repair or create heap
void SiftDown(uint32_t * a, size_t root, size_t end){
size_t parent;
size_t child;
// while at least two children
for(parent = root; (child = parent * 2 + 2) <= end; ){
// choose the larger child
if(a[child-1] > a[child])
child = child-1;
// if child > parent then swap, parent = child
if(a[child] > a[parent]){
std::swap(a[child], a[parent]);
parent = child;
// else done with search for swaps
} else {
break;
}
}
// check for final only child
if((child = parent * 2 + 1) <= end)
if(a[child] > a[parent])
std::swap(a[child], a[parent]);
}
链接地址: http://www.djcxy.com/p/40061.html
上一篇: Why space complexity of heap sort is O(1)?
下一篇: Difference in Space Complexity of different sorting algorithms