0

使用链表扩展哈希表会出现一些错误和警告。我想确保以下代码是正确的(扩展函数)并找出引发这些警告/错误的情况

编辑:感谢@nos,他注意到我的原型缺少我提到的警告+错误。不幸的是现在有这个:“在函数expand': undefined reference to添加'collect2:ld返回1退出状态

EDIT2:我注意到 add 函数返回一个 List* ,在 expand 函数中没有变量可以“获取”它。我在那里放了一个值......但错误仍然存​​在:/

EDIT3:分段错误:(使用gdb运行:*检测到glibc 损坏的双链表:0x0804c6b0 * * CORRECTED。添加了新的添加功能。

编辑:查找功能上 strcmp 上的分段错误。使用 gdb 运行:

(gdb) bt 已满

0 0x080487b9 在查找中(哈希表=0x804b008,哈希值=27,

number=0xbffff3f2 "6900101001") at pro.c:80
    list = 0xffffffff

1 0x0804883b 在添加(哈希表=0x804b008,

number=0xbffff3f2 "6900101001", name=0x804b6e0 "Irgaedggfs",

time=6943) 在 pro.c:96 new_elem = 0xffffffff hashval = 27

2 0x08048bc1 in main (argc=1, argv=0xbffff4b4) at pro.c:234

    number = "6900101001"
    name = 0x804b6e0 "Irgaedggfs"
    time = 6943
typedef struct 
{
     int length;        
     struct  List *head;    
} HashTable;

  //resolving collisions using linked lists - chaining
typedef struct 
{
     char *number;
     char *name;
     int time;
     struct List *next;
}List;



HashTable* expand( HashTable* h )
{    
          HashTable* new;
          int n;
          List *node,*next;
          PrimesIndex++;
          int new_size= primes[PrimesIndex];        /* double the size,odd length */

          if (!(new=malloc((sizeof( List*))*new_size))) return NULL;

          for(n=0; n< h->length; ++n) {
                for(node=h[n].head; node; node=next) {
                      add (new, node->number, node->name,node->time);
                      next=node->next;
                      free(node);
                }
          }
          free(h);
          return new;
}


int add ( HashTable* hashtable,char number[10],char* name,int time)
{
     List *new_elem;
    int hashval=hash (hashtable,number);

    new_elem=hashtable[hashval].head;
    if(hashtable[hashval].length>0) 
    {                   
          if ((lookup (hashtable,hashval,number))!=NULL) {return 0;}    
    }

    if (!(new_elem=malloc(sizeof(struct  List)))){ return -1;}

    //insert values for the new elem
    new_elem->number=strdup(number);    
    new_elem->name=strdup(name);
    new_elem->time=time;

    hashtable[hashval].head=new_elem;
    new_elem->next=NULL;
    hashtable[hashval].length++;

    /* rehash existing entries if necessary */
    if( TableSize(hashtable)>= 2*size]) 
    {    
         hashtable = expand(hashtable);
         if (hashtable ==NULL){
           return 0;
         }

    }
    return 1;
}



List *lookup ( HashTable *h ,int hashval,char number[10])
{
    List *list=h[hashval].head;
    for(list; list!=NULL; list=list->next){
            if (strcmp(number,list->number)==0)  //**SEGMENTATION**!!!!
                return list;

    }
    return NULL;
}
4

3 回答 3

1

您需要在调用函数之前声明它们。否则,C 将假定您的expand函数返回一个 int。

简单地说,在你的文件顶部,在你的结构声明之后,在你的函数定义之前,放置一个这样的原型。

 HashTable* expand( HashTable* h ,char number[10],char* name,int time);
于 2011-01-16T00:02:34.040 回答
0

在定义“expand”之前声明函数“add”,其中使用“add”。

List* add(HashTable* hashtable,char number[10],char* name,int time);

在这里定义展开..

在此处定义添加...

于 2011-01-16T01:44:57.683 回答
0

(我不知道如何更改计算机中的行;所以我必须发布一个新答案,而不是关注您的评论。对不起)

请尝试:

int add (HashTable** phashtable,char number[10],char* name,int time){

...

if(hashTableSize( *phashtable)== 2*(primes[PrimesIndex])){ 
     *phashtable = expand( *phashtable);
}

}

您可能需要相应地修改“add”和“add”的调用。

我不确定这是否会有所帮助。至少这是错误之一。

错误是如果在 add 调用中扩展 Hashtable,在 add 调用返回后,变量“hashtable”的值不会改变。

于 2011-01-16T03:16:23.367 回答