2014-06-16 79 views
1

这是我的一个链表结构:链表的帮助请求

typedef struct intervalo *Lista; 

typedef struct intervalo 
{ 
    int num; 
    Lista next; 
}Lista_int; 

这是我的代码的部分(我做了),破坏名单:

Lista destroi_lista_res(Lista lista) 
{ 
    Lista temp_ptr; 
    while (lista->next!= NULL) 
    { 
     temp_ptr = lista; 
     lista= lista->next; 
     free(temp_ptr); 
    } 
    free(lista); 
    return NULL; 
} 

不幸的是,我的程序当这个函数被调用时挂起。具体地说,while (lista->next!= NULL)永远不会终止。

我的问题:为什么这条线会导致无限循环?


附加代码的细节:

在main(),创建了两个列表。

/* Create linked list. */ 
Lista cria_lista_cab() 
{ 
    Lista aux; 
    aux=(Lista)malloc(sizeof(Lista_int)); 
    if(aux!=NULL) 
    { 
     aux->next=NULL; 
    } 
    return aux; 
} 

下列函数被用来添加数量的节点以结束两个列表:

/* Insert node at the list tail. */ 
void insere_elem(Lista *lista,int num) 
{ 
    Lista aux,ant_pos=*lista,pos=ant_pos->next; 
    aux=(Lista)malloc(sizeof(Lista_int)); 
    while(pos!=NULL) 
    { 
     ant_pos=ant_pos->next; 
     pos=pos->next; 
    } 
    aux->num=num; 
    aux->next=pos; 
    ant_pos->next=aux; 
} 

下一个函数结合了列表的数量节点,消除在增加数字顺序重复。返回结果列表:

Lista cria_lista_una(Lista lista1,Lista lista2) 
{ 
    Lista lista_res=cria_lista_cab(); 
    lista1=lista1->next; 
    lista2=lista2->next; 
    while(lista1!=NULL && lista2!=NULL) 
    { 
     if(lista1->num<lista2->num) 
     { 
      insere_elem(&lista_res,lista1->num); 
      printf("\n1 %d %d",lista1->num,lista2->num); 
      if(lista1!=NULL) 
       lista1=lista1->next; 
     } 
     else if(lista2->num<lista1->num) 
     { 
      insere_elem(&lista_res,lista2->num); 
      printf("\n2 %d %d",lista1->num,lista2->num); 
      if(lista2!=NULL) 
       lista2=lista2->next; 
     } 
     else if(lista2->num==lista1->num) 
     { 
      printf("\n3 %d %d",lista1->num,lista2->num); 
      if(lista1!=NULL) 
       lista1=lista1->next; 
      else if(lista2!=NULL) 
       lista2=lista2->next; 
     } 
    } 
    if(lista1!=NULL) 
    { 
     while(lista1!=NULL) 
     { 
      insere_elem(&lista_res,lista1->num); 
      lista1=lista1->next; 
     } 
    } 
    else if(lista2!=NULL) 
    { 
     while(lista2!=NULL) 
     { 
      insere_elem(&lista_res,lista2->num); 
      lista2=lista2->next; 
     } 
    } 
    return lista_res; 
} 

以下函数用于打印列表。

void imprime_lista_res(Lista lista) 
{ 
    lista=lista->next; 
    while(lista!=NULL) 
    { 
     printf("\nNum-> %d",lista->num); 
     lista=lista->next; 
    } 
} 

除了在清理时调用destroi_lista_res()并且程序挂起时,一切似乎都按预期运行。 。

+0

你看到的错误很可能在两个地方之一:要么调用这个函数的代码,要么代码创建链接列表,你能发布一个完全兼容的测试用例,展示你正在看到的问题吗? –

+0

我已经编辑了上面的代码,使用了我使用的所有功能 –

回答

0

给出代码:

void insere_elem(Lista *lista,int num) 
{ 
    Lista aux,ant_pos=*lista,pos=ant_pos->next; 
    aux=(Lista)malloc(sizeof(Lista_int)); 

,并记住利斯塔实际上是定义为 指针结构Lista_int

的实例您代码变为: 注意:您实际将节点追加到链接列表中,而不是插入

void insere_elem(struct Lista_int* *lista,int num) //note the ptr to ptr 
{ 
    struct Lista_int * aux; 
    struct Lista_int * ant_pos=*lista; //gets ptr to first instance of struct Lista_int 
    struct Lista_int * pos=ant_pos->next; // get ptr to NULL or second instance of.. 

    // get ptr to new instance of struct 
    aux=(struct Lista_int*)malloc(sizeof(Lista_int)); 

    // HERE should be checking that malloc() was successful 
    // otherwise, the lines: 
    // aux->num=num; 
    // aux->next=pos; 
    // will be writing to offsets from address 0 
    // will probably cause a crash 


    // step forward through linked list to find last struct 
    while(pos!=NULL) 
    { 
     ant_pos=ant_pos->next; // step ptr to prior struct 
     pos=pos->next;   // step ptr to current struct 
    } 

    aux->num=num; // set fields in new struct 
    aux->next=pos; // pos is already NULL, so probably (for clarity) just use NULL 
    ant_pos->next=aux; // set old struct instance ptr to new instance of struct 
} 

此外,关于这样的代码:

while(lista2!=NULL) 
{ 
    insere_elem(&lista_res,lista2->num); 
    lista2=lista2->next; 
} 

这个循环开始于头链表“lista_res” 所以在目前的链接列表中的每个元素,它增加了另一种元素 在一般, 这意味着链接列表的大小与此代码序列中的每个条目一样大小

3

这可能是因为lista为NULL开头。

更改功能:

Lista destroi_lista_res(Lista lista) 
{ 
    Lista temp_ptr; 
    while (lista!= NULL) 
    { 
     temp_ptr = lista; 
     lista= lista->next; 
     free(temp_ptr); 
    } 
    return NULL; 
} 
+0

我尝试了,但它给出了一个问题,在行lista = lista-> next,我执行调试,它提出了lista的地址是0xabababab,我不知道它是否是问题...我不'不明白,因为我已经运行lista与旅行和打印lista的元素,并打印所有元素没有问题... –

+3

魔术数字0xABABABAB被用于标记“没有人的在分配的堆内存之后“保护”字节。参考; http://www.nobugs.org/developer/win32/debug_crt_heap.html。看来你没有正确设置链接列表。如果你可以更多地使用你的代码,那将会很有帮助。 –

+0

我编辑了答案,添加了我使用的所有功能 –

0

在您的distroi函数中,如果Lista已经为NULL,那么它会做什么,然后它会通过分段错误。但根据你的说法,如果你是从这个功能中走出来的,那么你可能不会正确地创建你的列表。 先作如下变化:

Lista destroi_lista_res(Lista lista) 
{ 
    Lista temp_ptr; 
    while (lista!= NULL) 
    { 
     temp_ptr = lista; 
     lista= lista->next; 
     free(temp_ptr); 
    } 
    return NULL; 
} 

这是需要照顾的另一件事是,“有您创建列表正确,如果是,那么你打印功能将无法正常工作,做到确保此请做一个虚拟遍历函数用于调试目的,它只是像在你的distroi函数中一样遍历列表