C++ 从链表中的第一个节点删除时出现SEGFULT

C++ 从链表中的第一个节点删除时出现SEGFULT,c++,linked-list,C++,Linked List,删除第一个节点时,单链接链的删除功能不起作用。假设我有{33,40,50}当我尝试移除33时,我得到一个segfault,但其他两个工作正常。我想我只是需要一些新的眼睛来看看我在删除函数中搞砸了什么 删除函数 bool Set::remove(int X) { bool Flag = false; Node * Prev = Head; Node * Curr = Head->Succ; //unsigned Z = 0;

删除第一个节点时,单链接链的删除功能不起作用。假设我有{33,40,50}当我尝试移除33时,我得到一个segfault,但其他两个工作正常。我想我只是需要一些新的眼睛来看看我在删除函数中搞砸了什么

删除函数

bool Set::remove(int X)
{
        bool Flag = false;
        Node * Prev = Head;
        Node * Curr = Head->Succ;
        //unsigned Z = 0;

        while(Curr->Item != X)
        {
                Prev = Curr;
                Curr = Curr->Succ;
        }
        Prev->Succ =Curr->Succ;
        delete Curr;
        Num--;
        Flag = true;
        return Flag;
}

我想这是因为你从
Curr=Head->suc
开始,它已经超过了33(
Curr->item
是40)。你也从不检查它是否在列表的末尾。因此,您正在访问超出范围的内存。

我认为这是因为您从
Curr=Head->Succ>开始,它已经超过了33(
Curr->item
是40)。你也从不检查它是否在列表的末尾。因此,您正在访问超出范围的内存。

您应该检查是否已完成列表的末尾


您应该从第一个元素开始,而不是第二个元素(在本例中,第二个元素会导致您浏览列表并尝试继续下去)。

您应该检查是否浏览了列表的末尾


您应该从第一个元素开始,而不是从第二个元素开始(在本例中,第二个元素会导致您浏览列表并尝试继续进行下去)。

您在错误的位置开始搜索:

更改为:

    Node * Prev = Head;
    Node * Curr = Head->Succ;
致:

但是segfault真正的问题是,如果在链表中找不到指定的元素,您没有考虑终止条件的场景

您可以实现以下终止条件:

bool Set::remove(int X)
{
        Node * Prev = Head;
        Node * Curr = Head->Succ;
        while(Curr->Item != X)
        {
                Prev = Curr;
                Curr = Curr->Succ;
                if ( null == Curr ) {
                    // If you've reached the end of your
                    // linked list and haven't found the item
                    // yet, give up looking and return
                    return false;
                }
        }
        Prev->Succ =Curr->Succ;
        delete Curr;
        Num--;
        return true;
}

注意:我还清理了您的代码,删除了
bool标志,因为这是不必要的。

您在错误的位置开始搜索:

更改为:

    Node * Prev = Head;
    Node * Curr = Head->Succ;
致:

但是segfault真正的问题是,如果在链表中找不到指定的元素,您没有考虑终止条件的场景

您可以实现以下终止条件:

bool Set::remove(int X)
{
        Node * Prev = Head;
        Node * Curr = Head->Succ;
        while(Curr->Item != X)
        {
                Prev = Curr;
                Curr = Curr->Succ;
                if ( null == Curr ) {
                    // If you've reached the end of your
                    // linked list and haven't found the item
                    // yet, give up looking and return
                    return false;
                }
        }
        Prev->Succ =Curr->Succ;
        delete Curr;
        Num--;
        return true;
}

注意:我还对代码进行了一些清理,删除了
bool标志,因为它是不必要的。

Curr变量从第二个位置开始。Head指向第一个位置,Curr指向Head指向第二个位置的位置。这会产生一个无限循环并使程序崩溃。在
头部开始
curr
,而不是此您的curr变量从第二个位置开始。Head指向第一个位置,Curr指向Head指向第二个位置的位置。这会产生一个无限循环并使程序崩溃。在
头部启动
curr
,而不是该curr被初始化:

Node * Curr = Head->Succ;
意思是当你

while(Curr->Item != X)
您正在跳过“head”值。因为Curr->Item永远不会是33(head值),所以您将一直成功,直到最终到达列表末尾的空指针。 您没有检查while中是否已到达列表的末尾,因此执行此操作时会出现分段错误

Curr->Item != X
OR
Curr = Curr->Succ;
尝试初始化:

Node * Curr = Head;
Curr已初始化:

Node * Curr = Head->Succ;
意思是当你

while(Curr->Item != X)
您正在跳过“head”值。因为Curr->Item永远不会是33(head值),所以您将一直成功,直到最终到达列表末尾的空指针。 您没有检查while中是否已到达列表的末尾,因此执行此操作时会出现分段错误

Curr->Item != X
OR
Curr = Curr->Succ;
尝试初始化:

Node * Curr = Head;

也许你需要“curr”和“next”而不是“prev”和“curr”?
curr
开始指向
40
;它永远不会指向
33
。您真的需要这个标志变量吗?我想你错过了什么。无限循环?如果您试图
删除列表中未列出的值,您认为会发生什么情况?仅供参考-除非您是为了学校或嵌入式设备或类似设备而这样做的,您担心严重的大小/内存/性能限制,你可能应该使用STL的
std::list
而不是重新发明轮子。也许你需要“curr”和“next”来代替“prev”和“curr”?
curr
开始指向
40
;它永远不会指向
33
。您真的需要这个标志变量吗?我想你错过了什么。无限循环?如果您试图
删除列表中未列出的值,您认为会发生什么情况?仅供参考-除非您是为了学校或嵌入式设备或类似设备而这样做的,您担心严重的大小/内存/性能限制,您可能应该使用STL的
std::list
而不是重新发明轮子。我添加了一个if,在进入循环之前检查X是否存在,但我仍然在
Prev->suc=Curr->suc我理解,但我不确定如何修复。@sharkman检查更新的答案,它向您展示了在这种情况下实现终止条件的一种方法。谢谢您的帮助,但没有任何区别。但是,如果我最初将prev和curr都更改为head。它实际上会更新33,但对于某个随机数(我假设它是int中的内存地址),在进入循环之前,我添加了一个if来检查X是否存在,但我仍然在
Prev->suc=Curr->suc我理解,但我不确定如何修复。@sharkman检查更新的答案,它向您展示了在这种情况下实现终止条件的一种方法。谢谢您的帮助,但没有任何区别。但是,如果我最初将prev和curr都更改为head。它实际上会更新33,但会更新到某个随机数(我假设它是int格式的内存地址)