C++ 如何正确删除C++;
我感觉好像我没有真正删除节点并释放内存。我想我只是在移动指针,所以当我打印链接列表时,列表不会打印我删除的元素。所以我的问题是,我是真的在删除节点,还是只是简单地重新排列指针,使其看起来像是在删除节点(基本上只是断开链接,而不是删除节点)?谢谢你的帮助C++ 如何正确删除C++;,c++,linked-list,nodes,C++,Linked List,Nodes,我感觉好像我没有真正删除节点并释放内存。我想我只是在移动指针,所以当我打印链接列表时,列表不会打印我删除的元素。所以我的问题是,我是真的在删除节点,还是只是简单地重新排列指针,使其看起来像是在删除节点(基本上只是断开链接,而不是删除节点)?谢谢你的帮助 void SLL::deleteNode(int target){ Node *current = new Node; Node *previous = new Node; for (current = front->next, prev
void SLL::deleteNode(int target){
Node *current = new Node;
Node *previous = new Node;
for (current = front->next, previous = front; current != NULL; current = current->next, previous=previous->next){
if (previous->data == target && previous == front){
front = previous->next;
delete[] previous;
return;
//This if statement deletes the element if its the front
}
else {
if (previous->data == target && previous->next == NULL){
previous = NULL;
delete[] current;
return;
//This if statement deletes the node if it is the back
}
else if (current->data==target)
{
previous->next = current->next;
delete[] current;
return;
//This if statement deletes a node if it is in the middle
}
}
}
delete[] current;
delete[] previous;
}
此代码导致内存泄漏-您永远不会删除此内存。您可以在不分配内存的情况下声明指针:
Node *current = nullptr;
Node *previous = nullptr;
delete
将删除指针的内存,因此您将实际删除节点。
但是用于节点*
是不正确的,它应该只用于阵列-使用新[]
分配的内存。使用不当会导致未定义的行为。
因此,要正确删除节点,请使用操作符delete删除节点
使用内存泄漏检测工具了解您的程序中是否存在内存泄漏
删除列表元素的代码:比如说,我们有一个指向列表头部的pHead
(但如果你自己写这些东西,你会得到更多):
使用指针指向指针的替代方法(社区添加) 当您使用列表中的实际指针执行枚举时,上面的内容可能会有新的含义。下面从
pp
开始,分配头指针的地址(不是它指向的节点,而是实际指针本身)。我们遍历列表,直到pp
保存指向要删除目标节点的指针的地址(可能是头指针,也可能是某个节点中的下一个指针,没有区别)。正在寻址的指针设置为其自身节点的next
值,然后删除目标节点
这确实应该在调试器中观察,看看它是如何工作的,但考虑到实际情况,该算法非常简单:
Node **pp = &pHead;
while (*pp && (*pp)->data != target)
pp = &(*pp)->next;
if (*pp)
{
Node *victim = *pp;
*pp = victim->next;
delete victim;
}
就这些。你可以在不需要特殊情况下免费移除头部节点。希望这也能有所帮助。当您将当前
和上一个
声明为单个实例时,为什么要使用数组删除(delete[]
)版本?使用front->next
启动枚举算法与此有关。请告诉我们,您使用的不是实际不包含数据的预分配“头”节点。不需要它。除非您为节点分配了新节点[n]
,否则您使用的删除操作符是错误的。我不知道。我试过这个,它奏效了。请回答这个问题。不知道是什么?您的前指针是否为sentinel节点?是否为您的节点分配了vector-new
?代码是你写的,对吗?顺便说一句,你在这个函数的开头分配的两个节点立即被泄漏,所以我可以向你保证,不管你是否删除了一个目标节点,最终都会有零内存被回收。你delete[]
在你的第二个块中有一个空向量,但我认为控件永远无法进入那个块,所以我想这是没有意义的。谢谢。从现在起,我将不再为他们使用新的。尽管我的问题仍然存在,但如何删除目标节点?我知道你提到过它,但你能再解释一下吗?@user3291106-我提供了一个示例代码。但是如果你自己写的话,那会更有用。现在试试双链接列表,比如说,从末尾搜索。@Alex当pHead
指向将被删除的节点时,这是如何完成的?Follow:将跳过while循环,不执行任何操作pHead->next
将有效地分配给自身,因为pPrev
、pCur
和pHead
都指向同一节点。然后使用delete pCur销毁头部节点代码>,从而孤立列表的整个剩余部分,并使所有三个指针保留无效、不确定的地址。一句话,哎哟。@WhozCraig谢谢你的更正!修好了。虽然我更希望用户3291106告诉我:)我不需要急于写代码,同意。@Alex没问题。看一下附录。不知道你以前是否见过它,但它值得一看。和+1表示坚持回答。
Node* pCur = pHead;
Node* pPrev = pCur;
while (pCur && pCur->data != target) {
pPrev = pCur;
pCur = pCur->next;
}
if (pCur==nullptr) // not found
return NOT_FOUND;
if (pCur == pHead) { // first element matches
pHead = pCur->next;
} else {
pPrev->next = pCur->next;
}
// pCur now is excluded from the list
delete pCur; // deallocate its memory
Node **pp = &pHead;
while (*pp && (*pp)->data != target)
pp = &(*pp)->next;
if (*pp)
{
Node *victim = *pp;
*pp = victim->next;
delete victim;
}