双链表中的删除

deletion in doubly linked list

本文关键字:删除 链表      更新时间:2023-10-16

每当我调用这个函数时,我的程序就会崩溃。我调试了它,这是因为start=start->next的行;我还是想不出哪里出了问题。我的开始是节点的全局指针。

void double_llist::delete_element(string value)
{
      node *tmp, *q;
      //first element
     if (start->info == value)
     {
         tmp = start;
         start = start->next;
         start->prev = NULL;
         cout<<"Element Deleted"<<endl;
         delete tmp;
         return;
     }
     q = start;
     while (q->next->next != NULL)
     {
         //nth element
         if (q->next->info == value)
         {
             tmp = q->next;
             q->next = tmp->next;
             tmp->next->prev = q;
             cout<<"Element Deleted"<<endl;
             delete tmp;
             return;
         }
         q = q->next;
     }
     //last element
     if (q->next->info == value)
     {
         tmp = q->next;
         delete tmp;
         q->next = NULL;
         cout<<"Element Deleted"<<endl;
         return;
     }
     cout<<"Element "<<value<<" not found"<<endl;
 }

您的函数过于复杂,无法检查节点是否等于NULL。

例如,通常start可以等于NULL,或者start->next可以等于NULL等等

考虑一下函数中的代码片段就足够了

 if (start->info == value)
 {
     tmp = start;
     start = start->next;
     start->prev = NULL;
     cout<<"Element Deleted"<<endl;
     delete tmp;
     return;
 }

首先,start可以等于NULL。所以这个声明

if (start->info == value)

或者这个语句

start = start->next;

已经错了。

或者start->next可以等于NULL。在这种情况下,下面的语句中的第二个语句

     start = start->next;
     start->prev = NULL;

也是错误的。

考虑到通常双链接列表支持指向尾部(或末端)节点的指针。

这个函数可以写得简单得多。

例如

void double_llist::delete_element( std::string value )
{
    node *current = start;
    while ( current && current->info != value ) current = current->next;
    if ( current )
    {
        if ( !current->prev )
        {
            start = current->next;
        }
        else
        {
            current->prev->next = current->next;
        }
        if ( !current->next )
        {
            // end = current->prev;
        }
        else
        {
            current->next->prev = current->prev;
        }
        delete current;
    }
    else
    {
        std::cout << "Element " << value << " not found" << std::endl;
    }
}                 

在这个程序中,我评论了一条语句,如果您的列表支持指向列表最后一个节点的指针,则应该取消注释。

您的问题可能是:

if (start->info == value)
{
    tmp = start;
    start = start->next;
    start->prev = NULL;  // This line !!!!!
    cout<<"Element Deleted"<<endl;
    delete tmp;
    return;
}

在使用start之前,您需要检查四个nullptr

也许这会有所帮助:

void double_llist::delete_element(string value)
{
     if (start == NULL) return;  // New line
     node *tmp, *q;
     //first element
     if (start->info == value)
     {
         tmp = start;
         start = start->next;
         if (start != NULL)  // New line
         {
             start->prev = NULL;
         }
         cout<<"Element Deleted"<<endl;
         delete tmp;
         return;
     }
     q = start;
     while (q->next->next != NULL)
     {
         //nth element
         if (q->next->info == value)
         {
             tmp = q->next;
             q->next = tmp->next;
             tmp->next->prev = q;
             cout<<"Element Deleted"<<endl;
             delete tmp;
             return;
         }
         q = q->next;
     }
     //last element
     if (q->next->info == value)
     {
         tmp = q->next;
         delete tmp;
         q->next = NULL;
         cout<<"Element Deleted"<<endl;
         return;
     }
     cout<<"Element "<<value<<" not found"<<endl;
 }

BTW:我想这是某种家庭作业。如果不是,那就停止制作你自己的链接列表!请使用其中一个标准容器,例如vector、list、deque。