C++ 当我调用解构器时,这是否会导致内存泄漏?
我有一个数据结构项目,我必须为我的Uni类做,这是实现一个带有链表的堆栈;简单的东西。我们得到了一些代码方面的帮助,向我们展示了实现这种结构的正确方法 堆栈类:C++ 当我调用解构器时,这是否会导致内存泄漏?,c++,C++,我有一个数据结构项目,我必须为我的Uni类做,这是实现一个带有链表的堆栈;简单的东西。我们得到了一些代码方面的帮助,向我们展示了实现这种结构的正确方法 堆栈类: class Stack { public: Stack(void) { top = NULL; // Initialises defualt top node pointer. } ~Stack(void) { while (NodePop() != NU
class Stack
{
public:
Stack(void)
{
top = NULL; // Initialises defualt top node pointer.
}
~Stack(void)
{
while (NodePop() != NULL){}
}
void Push(int value) // Pushes a new node onto the stack.
{
Node* temp = new Node(value, top); // Creates a temporary node with a value and makes it
// point to the top node as the next node in the stack.
top = temp; // Temporary node becomes the top node in the stack.
}
Node* NodePop(void)
{
/* Remove top node from the stack */
Node* temp = top; // Creates a temporary node to return, sets it to top node.
if (top != NULL) top = top->getNext(); // Points the stacks top node to the next node in the list.
return temp; // Returns a pointer to the popped node still in the heap.
}
int Pop(void) // Pops the top node off of the stack. Returns the nodes value.
{
Node* temp = NodePop();
int valueReturn = 0;
/* Sets the return value */
if (temp != NULL)
{
valueReturn = temp->getVal(); // Set return value to the nodes value if there is a node left.
}
else
{
throw "Stack Empty"; // Throws exception if temp is NULL and stack is empty.
}
delete temp; // Deletes the node entirely from the heap.
return valueReturn;
}
private:
Node* top;
};
节点类:
class Node
{
public:
Node(int value, Node* nextptr = NULL, Node* prevptr = NULL, int currentpriority = 0)
{
/* Set initial variables for the node at creation */
this->value = value;
this->next = nextptr;
this->prev = prevptr;
this->priority = currentpriority;
}
// bunch of getters and setters...
private:
Node* next; // Pointer to the next node.
Node* prev; // Pointer to the previous node.
int priority; // Stores the node priority as a number 0-9.
int value; // Stores the node value for printing.
};
我们不能改变任何类结构(我也很讨厌,NodePop()应该是私有的,但是w/e)
因此,这里的NodePop()实际上是从列表中删除顶部节点,但不删除它;它从链表中删除对它的所有引用,但它从不从堆中删除它,它只从Pop()中的堆中删除。这一切都很好(除了能够公开调用NodePop(),但同样,我不允许将其设置为私有)。但是当我调用析构函数时,它必须使用NodePop(),而不是Pop()
那么这是否意味着当nodeop()从析构函数运行时,该节点永远不会从堆中删除?
如果是这样,我将如何删除它们,因为它将运行nodePop(),如果我在一段时间内有它,则执行while,或者如果语句条件是这样,则始终有一个节点未删除?确实,节点未被删除,并且此代码将泄漏。您可以使用Valgrind之类的工具来验证这一点 我将
while
更改为while(Node*N=NodePop())delete N代码>
仅供参考,此代码绝对不是惯用的C++11。它基本上是写得很糟糕的C语言,我希望能在其中发现更多的bug。你的老师应该因为像这样展示C++11而受到惩罚:-)看看有问题的代码
~Stack(void)
{
while (NodePop() != NULL){}
}
Node* NodePop(void)
{
/* Remove top node from the stack */
Node* temp = top; // Creates a temporary node to return, sets it to top node.
if (top != NULL) top = top->getNext(); // Points the stacks top node to the next node in the list.
return temp; // Returns a pointer to the popped node still in the heap.
}
析构函数调用NodePop(),直到该函数返回NULL。让我们看看NodePop()的作用。代码中的注释声称它创建了一个临时节点以返回不正确的。它创建一个指向节点(节点*)的指针,并将该指针设置为指向top
所指向的位置。如果top
不为空,它将top
设置为指向top的下一个节点。它返回temp
,这是一个指向最初顶部节点的指针
在任何情况下都不会释放与任何节点关联的内存,因此存在内存泄漏
您可以通过删除析构函数中不为NULL的每个节点*来修复漏洞。感谢您的回答,我不知道您可以在while循环条件中创建变量,但我还是编程新手。不用担心。我可以推荐这本书给新C++程序员:——由C++发明者制作,它涵盖了现代C++设计。你所给的代码有很多错误,内存泄漏是什么?还是一千?很遗憾,在大学里,作为C++的例子,这是一个耻辱。Stroustrup在他的主旨中提到了这个问题,老师教坏C作为C++的介绍。我会对自己和你自己说一句话,然后写一张便条,问这是不是叫POP而不是NoDopp,因为这样会漏掉。谢谢你的回答。我的代码中的注释很糟糕,在我完成之前,我仍然需要重新做一些注释,我知道这是一个指针。