2012-10-08 153 views
0

我有一个女巫堆排序问题。我不知道我的代码有什么问题。这个程序只改变了表中的第二个和最后一个位置。这是我的代码(没有主要功能):堆排序heapify排序

#include<stdio.h> 
#define DUZO 100000000 
int heap_size; 
int tab[DUZO]; 

void heapify(int start){ 
    int l, r, largest, pom; 

    l = 2*start + 1; 
    r = 2*start + 2; 

    if((l < heap_size) && (tab[l] > tab[start])) 
     largest = l; 
    else 
     largest = start; 

    if((r < heap_size) && (tab[r] > tab[largest])) 
     largest = r; 
    if(largest != start){ 
     pom = tab[start]; 
     tab[start] = tab[largest]; 
     tab[largest] = pom; 

     heapify(largest); 
    } 
} 

void build_max(){ 
    int lenght, i; 
    lenght = heap_size; 

    for(i = ((lenght - 1)/2); i >= 0; --i){ 
     heapify(i); 
    } 
} 

void heap_sort(){ 
    int i; 
    build_max(); 


    for(i = heap_size-1; i > 0; --i) { 
     int tmp = tab[0]; 
     tab[0] = tab[i]; 
     tab[i] = tmp; 
     --heap_size; 
     heapify(0); 
    } 
} 

感谢您的一切帮助。

+1

如果您逐行添加解释每个语句,循环和函数的*目的*的注释,它可能会帮助他人阅读此代码。在这样做的过程中,您可能会发现代码实际执行的地方与您打算执行的操作不一致。 –

+0

为什么不仅仅使用许多现有的heapsort实现之一而不是试图编写自己的? –

+0

同意,有人在评论中标记为close。我将标记为保持打开状态,但您应该添加注释并显示输出(使用小型输入数据集)并提供一个主体,以便它可以在不进行编辑的情况下运行。 –

回答

1
int heap_size = 6; 
int tab[5]; 

这要求写入(和阅读)过去的数组的末尾,导致与可能不好的后果不确定的行为。

将堆大小和数组作为全局变量是一个坏主意,它们应该是函数的参数。

l = 2*start + 1; 
r = 2*start + 2; 

这是因为当你有堆的索引0处的顶部的索引,但

if((l <= heap_size) && (tab[l] > tab[start])) 

是检查是否有堆的顶部索引1.对于指数将使用0,那应该是<(也在下一个检查r)。

void build_max(){ 
    int lenght, i; 
    lenght = heap_size; 

    for(i = ((lenght - 1)/2); i > 0; i--){ 
     heapify(i); 
    } 
} 

忘记heapify顶部,所以它不一般的创建一个堆,条件应该是i >= 0

void heap_sort(){ 
    int i, lenght; 
    build_max(); 
    lenght = heap_size; 

    for(i = lenght; i > 1; i--){ 
     heap_size -= 1; 
     heapify(i); 
    } 
} 

不交换最后一个位置的堆顶部,所以它根本不排序。循环应该看起来像

for(i = heap_size-1; i > 0; --i) { 
    /* swap top of heap in the last position */ 
    int tmp = tab[0]; 
    tab[0] = tab[i]; 
    tab[i] = tmp; 
    --heap_size; /* urk, but what can we do if heapify uses the global? */ 
    heapify(0); /* we need to heapify from the top, since that's where the leaf landed */ 
} 

实际上排序数组。

+0

“,如果您在索引1处有堆的顶部,那么将使用该检查。对于索引0,应该是<(也在下一个r检查中)”在哪个地方我必须更改<? – henio180

+0

在'if((l <= heap_size)'和'r'的对应行另一件事是,一旦你开始在最后一个位置交换堆顶部,你需要调用'heapify(0)' 'heapify(i)',因为叶被交换到位置0. –

+0

好的我已经改变了它,但它仍然没有工作:( – henio180