Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/design-patterns/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 删除双链接列表中的函数故障_C++_Linked List_Doubly Linked List - Fatal编程技术网

C++ 删除双链接列表中的函数故障

C++ 删除双链接列表中的函数故障,c++,linked-list,doubly-linked-list,C++,Linked List,Doubly Linked List,我从双链接列表中删除节点的功能是向列表中添加(覆盖?)值,该值在打印列表时显示 下面列出了主要、删除和打印功能的代码。预期输出以及当前代码与其输出之间的相关性也如下所示 主设备代码 在main中,调用add函数,并将参数中的整数作为节点添加到链表中。添加功能与打印功能一样有效 int main() { LinkedList aList; aList.add(3); aList.add(10); aList.add(1); aList.add(7);

我从双链接列表中删除节点的功能是向列表中添加(覆盖?)值,该值在打印列表时显示

下面列出了主要、删除和打印功能的代码。预期输出以及当前代码与其输出之间的相关性也如下所示

主设备代码 在main中,调用add函数,并将参数中的整数作为节点添加到链表中。添加功能与打印功能一样有效

int main()
{
    LinkedList aList;

    aList.add(3);
    aList.add(10);
    aList.add(1);
    aList.add(7);
    aList.add(9);
    aList.add(12);
    aList.printAscending();
    aList.printDescending();
    aList.remove(3);
    aList.remove(1); //The integer to be removed with this line ends up in the output
    aList.remove(7);
    aList.remove(12);
    cout << "remove operations should be complete" <<endl;
    aList.printAscending();
    aList.printDescending();

    return 0;
}
打印功能代码 实际产量
如果调用
int main
以删除整数1
aList.remove(1)
被替换为
aList.remove(999)
,则整数999将显示在降序打印的实际输出中,而不是1。但是,整数0始终被追加到升序打印中。

删除
curr
后,将取消对其的引用:

curr = curr->next;

这是未定义的行为

在删除
curr
后,将其取消引用:

curr = curr->next;

这是未定义的行为

以及Beta指出的未定义的行为,头部和尾部的特殊情况都有问题。通过调试器运行此操作,并在每次删除后检查列表中的值,将向您显示出出错的地方

此代码:

        else if(curr == tail)
        {
            tail = tail->prev;
            curr->prev = NULL;
            delete curr;
        }
不使用最后一个元素的
next
指针执行任何操作。这意味着您的第二个最后一个元素(随后成为最后一个元素)有一个指向已释放内存的
next
指针

要修复它,您需要将最后一个元素的
next
指针设置为null。大概是这样的:

        else if(curr == tail)
        {
            tail = tail->prev;
            tail->next = NULL;
            curr->prev = NULL;
            delete curr;
        }
但是等等!(几乎*)不能保证前一个元素存在(即在1个元素列表中),因此需要检查新的尾部是否为空

        else if(curr == tail)
        {
            tail = tail->prev;
            if (tail != NULL)
               tail->next = NULL;
            curr->prev = NULL;
            delete curr;
        }
*实际上,如果这是一个单元素列表,您将无法访问此代码,您可能已经通过了“head”if测试代码,它有一个类似的问题,即它不会更改第二个节点的
prev
指针

因此,您还需要在“head”if测试代码中执行相同类型的测试


一旦这样做了,您可能会发现您可以重新安排测试以消除重复代码。

以及Beta指出的未定义行为,您的头和尾的特殊情况都有问题。通过调试器运行此操作,并在每次删除后检查列表中的值,将向您显示出出错的地方

此代码:

        else if(curr == tail)
        {
            tail = tail->prev;
            curr->prev = NULL;
            delete curr;
        }
不使用最后一个元素的
next
指针执行任何操作。这意味着您的第二个最后一个元素(随后成为最后一个元素)有一个指向已释放内存的
next
指针

要修复它,您需要将最后一个元素的
next
指针设置为null。大概是这样的:

        else if(curr == tail)
        {
            tail = tail->prev;
            tail->next = NULL;
            curr->prev = NULL;
            delete curr;
        }
但是等等!(几乎*)不能保证前一个元素存在(即在1个元素列表中),因此需要检查新的尾部是否为空

        else if(curr == tail)
        {
            tail = tail->prev;
            if (tail != NULL)
               tail->next = NULL;
            curr->prev = NULL;
            delete curr;
        }
*实际上,如果这是一个单元素列表,您将无法访问此代码,您可能已经通过了“head”if测试代码,它有一个类似的问题,即它不会更改第二个节点的
prev
指针

因此,您还需要在“head”if测试代码中执行相同类型的测试


一旦你这样做了,你可能会发现你可以重新安排测试以消除重复的代码。

你能解释一下吗?删除后你如何取消引用
curr
?@0x1000001:你这样取消引用:
curr->next
以这种方式取消引用
curr
有什么不正确的地方吗?i、 e,为什么会导致未定义的行为?修复方法是什么?删除节点后,不应取消引用
curr
。您应该删除找到的节点,然后将其从循环中断开,或者在没有找到任何内容的情况下继续搜索<代码>如果(curr->data==val){删除节点并中断循环}否则curr=curr->next。您能解释一下吗?删除后如何取消对
curr
的引用?@0x1000001:您这样取消引用:
curr->next
以这种方式取消对
curr
的引用有什么不正确之处?i、 e,为什么会导致未定义的行为?修复方法是什么?删除节点后,不应取消引用
curr
。您应该删除找到的节点,然后将其从循环中断开,或者在没有找到任何内容的情况下继续搜索<代码>如果(curr->data==val){删除节点并中断循环}否则curr=curr->next。谢谢,这是降序打印问题的答案。谢谢,这是降序打印问题的答案。