2014-12-07 106 views
0

我使用的函数malloc和初始化一些存储器的哈希函数,如下所示:返回一个指针,指向在一个函数malloc分配的结构

int main (int argc, char * argv []) 
{ 
    Bucket * hashTable; 
    hashTable = createHashTable(); 
    ... 
在“main.c中”

称为在另一个文件中的函数是这样的:

Bucket * createHashTable() 
{ 
    Bucket * hashTable = malloc (sizeof(Bucket) * HASHSIZE); 
    int c=0; 
    for (c=0;c<HASHSIZE;c++) 
    { 
    hashTable[c].key=NULL; 
    hashTable[c].text=NULL; 
    hashTable[c].next=NULL; 
    } 
    return hashTable; 
} 

我的程序与“-pedantic -Wall”,但段错误完全编译。用gdb,我得到这个:

Reading symbols from hash...done. 
(gdb) break 11 
Breakpoint 1 at 0x400990: file main.c, line 11. 
(gdb) run 
Starting program: /home/user/Projects/random/hash 

Breakpoint 1, main (argc=1, argv=0x7fffffffdf78) at main.c:11 
11 hashTable = createHashTable(); 
(gdb) print hashTable 
$1 = (Bucket *) 0x400520 <_start> 
(gdb) print * hashTable 
$2 = { 
key = 0x89485ed18949ed31 <error: Cannot access memory at address 0x89485ed18949ed31>, 
text = 0x495450f0e48348e2 <error: Cannot access memory at address 
0x495450f0e48348e2>, next = 0xc74800400a90c0c7} 
(gdb) 

与结构“斗”的定义标题的部分:

typedef struct bucket{ 
    char * key; 
    char * text; 
    struct bucket * next; 
} Bucket; 

这是一个范围的问题吗?当功能完成后,它是否会损坏我的malloc'ed内存或什么?

平台是64位Linux,而这次从malloc()返回的地址是0x1665010--我想如果它失败了,它将是NULL。

编辑:在这之后的下一个功能,在main.c中,尝试添加到表中的条目:

printf("Adding banana...\n"); 
addItem("Banana", "Bananas are yellow", &hashTable); 

(是啊,是啊 - 香蕉,我知道)的功能是:

void addItem(char * key, char * data, Bucket ** table) 
{ 
    unsigned int hashkey; 
    hashkey=hash(key); 
    printf("%lu\n",strlen(key)); 
if (!table[hashkey]->text) /* SEGFAULTS HERE */ 
{ 
    table[hashkey]->key=key; 
    table[hashkey]->text=data; 
} 
else 
{ 
    Bucket * newListElement = malloc(sizeof(Bucket)); 
    newListElement->key=key; 
    newListElement->text=data; 
    newListElement->next = NULL; 
    table[hashkey]->next = newListElement; 
} 

}

+0

这似乎有效。你在哪个平台上? 'malloc'返回一个有效的地址还是失败(返回NULL)? – slugonamission 2014-12-07 21:04:20

+0

为了帮助您验证这一点,您应该提供一个完整的最简单示例。例如,你包含哪些头文件? “Bucket”的定义是什么?等等... – glglgl 2014-12-07 21:05:21

+0

等等,你确定它在这条线上崩溃了吗?执行该行之前,您对GCC的'break 11'命令将会中断*。 – slugonamission 2014-12-07 21:06:37

回答

1

这条线:

if (!table[hashkey]->text) 

应该是:

if (!(*table)[hashkey]->text) 

并且类似地对以下行。在这个函数中,table实际上是一个指向main中名为hashTable的变量的指针。

解决此错误的另一种方法是使该函数为Bucket *,而不传递hashTable的地址。似乎没有任何功能需要知道hashTable的地址,因为它只是把东西放在表格中。

+0

这工作,这很好,谢谢!这是否意味着它是按值传递的,因此对表的更新不会超出函数范围? – Andomonir 2014-12-07 21:51:27

+1

你不会更新函数中任何地方的'table'(除非你有更多的代码没有发布)。不要将'table'与'table'指向的东西混淆。 – 2014-12-07 23:29:57

0

我试图重现此问题,但无法成功。

所以我唯一的猜测是你可能已经省略了向主模块提供正确的功能签名,并且在那里它被称为int createHashTable()。这应该导致一个警告,并且会让你失去你的结果指针IFF的高32位,你有64位指针和一个32位的int

相关问题