C双向链表删除中间节点无法打印

C数据结构双向链表节点删除问题。
出现错误的模块是中间节点(至少3个)的删除,该节点后续无法打印(我根据返回值查到的错误可能是栈溢出

//tmp指向  前驱的后继指向 删除的后继  删除后继的前驱指向删除的前驱
//空表无删除 
//只有一个置为NULL 
//删首节点 不需要前驱节点的操作
//删尾结点 不需要后驱节点的操作 
void Delete_list(Node **phead , int num)//后者为待删除节点对应键值 
{
    Node *tmp  = (Node *) malloc (sizeof(Node));
    Node *p = *phead;
    int flag;
    
    if(!p)
    printf("此表为空");
    else
    {
        if(!( p -> next))//单一节点判断 
        {
            if(p -> data = num)
            {
                flag = 1;
                *phead = NULL;
            }
         }
         //非单一节点 
         else
         {
             if((*phead)-> data == num)
             {
                 flag =1;
                 tmp = (*phead);
                 (*phead) = (*phead)->next;//运算符 * 取地址的优先级很低 因此使用尽量加括号 
                 (*phead)->prior=NULL; 
                 free(tmp);
                 
              } 
              else
              {
                  while(p->next)
                  {
                      
                      if(p -> data == num)
                      {
                          flag =1;
                          tmp = p;
                          printf("%d %d",p->prior->data,p->next->data);
                          Node *test1,*test2;
                          
                          tmp -> prior-> next = tmp->next;
                          tmp -> next-> prior = tmp->prior;
                          
                        test1= tmp -> prior-> next;//4
                          test2 =tmp -> next-> prior;//2
                          printf("\n%d %d",test1->data,test2->next->data);
                                                
                          free(tmp);
                          break;
                    }
                    p = p -> next;    
                 }
                 if(p->data == num)
                 
                 {
                     flag = 1;
                    tmp = p;
                    p -> prior -> next = NULL;
                    free(tmp);  
                 }
              }
             
          } 
     } 
    
}

img

双链表我将删除节点的前后节点重新相连为何断链了,但是test测试又表明实际相连,我想请问一下这是哪里出现问题了?

题主想的复杂了,修改完善如下,供参考:

void Delete_list(Node** phead, int num)
{
    Node* p = *phead;
    if (!p)
        printf("此表为空");
    else{
        while (p) //while (p->next)
        {
            if (p->data == num)
            {
                if (p == (*phead)){   //链表第一个结点
                    (*phead) = p->next;
                    if(p->next)
                        p->next->prior = NULL;
                }
                else if (!p->next){   //链表最末尾结点
                    p->prior->next = NULL;
                }
                else{
                    p->prior->next = p->next;
                    p->next->prior = p->prior;
                }
                free(p);
                break;
            }
            p = p->next;
        }
    }
}

回答:应该是最后一部分的代码写错了,修改一下试试

img

//tmp指向  前驱的后继指向 删除的后继  删除后继的前驱指向删除的前驱
//空表无删除 
//只有一个置为NULL 
//删首节点 不需要前驱节点的操作
//删尾结点 不需要后驱节点的操作 
void Delete_list(Node** phead, int num)//后者为待删除节点对应键值 
{
    Node* tmp = (Node*)malloc(sizeof(Node));
    Node* p = *phead;
    int flag;

    if (!p)
        printf("此表为空");
    else
    {
        if (!(p->next))//单一节点判断 
        {
            if (p->data = num)
            {
                flag = 1;
                *phead = NULL;
            }
        }
        //非单一节点 
        else
        {
            if ((*phead)->data == num)
            {
                flag = 1;
                tmp = (*phead);
                (*phead) = (*phead)->next;//运算符 * 取地址的优先级很低 因此使用尽量加括号 
                (*phead)->prior = NULL;
                free(tmp);
            }
            else
            {
                while (p->next)
                {
                    if (p->data == num)
                    {
                        flag = 1;
                        tmp = p;
                        printf("%d %d", p->prior->data, p->next->data);
                        Node* test1, * test2;

                        tmp->prior->next = tmp->next;
                        tmp->next->prior = tmp->prior;

                        test1 = tmp->prior->next;//4
                        test2 = tmp->next->prior;//2
                        printf("\n%d %d", test1->data, test2->next->data);

                        free(tmp);
                        break;
                    }
                    p = p->next;
                }
                if (flag == 0 && p->data == num)
                {
                    flag = 1;
                    tmp = p;
                    p->prior->next = NULL;
                    free(tmp);
                }
            }
        }
    }
}

你好,我自己后面把它拆分为子模块调试了发现可能是 条件判断的划分导致的问题;

那个if的判断,是用来判断尾结点, 因为尾结点不需要有后驱的prior更改

如下:是我修改之后的代码运行无误 但是对于修改前 可能的栈溢出问题 我也不知道是如何导致的 欢迎交流


```c
if(!p)
    printf("此表为空");
    else
    {
        if(!( p -> next))//单一节点判断 
        {
            if(p -> data = num)
            {
                flag = 1;
                *phead = NULL;
            }
         }
         //非单一节点 
         else
         {
        while(p->next)
        {
        
             if((*phead)-> data == num)
             {
                 flag =1;
                 tmp = (*phead);
                 (*phead) = (*phead)->next;//运算符 * 取地址的优先级很低 因此使用尽量加括号 
                 (*phead)->prior=NULL; 
                 free(tmp);
            
                 
              } 
              else
              {
                      
                      if(p -> data == num)
                      {
                          flag =1;
                          tmp = p;
                          //printf("%d %d",p->prior->data,p->next->data);
                          //Node *test1,*test2;
                          
                          tmp -> prior-> next = tmp->next;
                          tmp -> next-> prior = tmp->prior;
                          
                        //test1= tmp -> prior-> next;//4
                          //test2 =tmp -> next-> prior;//2
                          //printf("\n%d %d",test1->data,test2->next->data);
                                                
                          free(tmp);
                          break;
                    }
                    

              }
             p = p->next;
          } 
          
         if(p->data == num)
                 
                 {
                     flag = 1;
                    tmp = p;
                    p -> prior -> next = NULL;
                    free(tmp);  
                 }
     } 
}