i came into Assertion failure during running this program, and i really don't know why, hope you guys can help, thanks a lot ^^

The program is to copy a linked list from another, the Copy function may look complicated because i'm not experienced enough to simplify it.. Without the destructor, the program runs fine..

#include <iostream.h>

struct node
{
	int data ;
	node * next ;
};

class list
{
private:
	node *head ;
public:
	list() ;
	[B]//~list() ;[/B]
	node* Add(node *h , int d) ;
	node* Copy(node *& res , node * copy) ;
	void Input() ;
	void Display() ;
	node* GetHead() ;
	void AssignHead(node *h) ;
};

list::list()
{
	head = NULL ;
}

[B]/*list::~list()
{
	while(head)
	{
		node *current = head->next ;
		delete head ;
		head = current ; 
	}
}*/[/B]

node * list::GetHead()
{
	return head ;
}

void list::AssignHead(node *h)
{
	head = h ;
}

node * list::Add(node *h , int d)
{
	if ( !h )
	{
		h = new node ;
		h->data = d ;
		h->next = NULL ;
	}
	else
		h->next = Add(h->next , d) ;
	return h ;
}

void list::Input()
{
	int n ;
	int d ;
	cout << "How many intergers to input: " ;
	cin >> n ;

	for ( int i = 0 ; i < n ; ++i )
	{
		cout << "Interger #" << i+1 << ", please enter: " ;
		cin >> d ;
		head = Add(head,d) ;
	}
}

void list::Display()
{
	node * current = head ;
	while (current != NULL)
	{
		cout << current->data << " " ;
		current = current->next ;
	}

}

node * list::Copy(node *& res , node * copy)
{

	if (copy)
	{
		res = copy ;
		Copy(res->next,copy->next) ;
	}

	return res ;
}



int main()
{
	list integer , a ;

	integer.Input() ;

	integer.Display() ;
	cout << endl ;

	//a.Input() ;

	//a.Display() ;

	node *res = NULL ;
	a.AssignHead(a.Copy(res , integer.GetHead())) ;

	a.Display() ;

	return 0 ;
}

Dani AI

Generated

The crash is caused by a shallow copy: the Copy routine assigns the original nodes' pointers to the new list instead of allocating fresh nodes. That leaves two list objects sharing the same memory; when one list's destructor frees those nodes, the other later tries to access/delete already‑freed memory and an assertion or crash follows. This is the same root cause pointed out; 's snippet omitted the loop needed to free the whole chain.

Make the copy a true deep copy (allocate new nodes and copy the data). An iterative helper avoids recursion and is simple to reason about:

node* deep_copy(const node* src) {
    if (src == NULL) return NULL;
    node* head_copy = new node;
    head_copy->data = src->data;
    head_copy->next = NULL;
    node* tail = head_copy;
    for (const node* p = src->next; p != NULL; p = p->next) {
        node* n = new node;
        n->data = p->data;
        n->next = NULL;
        tail->next = n;
        tail = n;
    }
    return head_copy;
}

Use a destructor that walks and deletes every node (not just the first). For example:

list::~list() {
    node* cur = head;
    while (cur != NULL) {
        node* nxt = cur->next;
        delete cur;
        cur = nxt;
    }
    head = NULL;
}

Follow the Rule of Three: implement a copy constructor and copy‑assignment operator that use the deep copy helper (and guard against self‑assignment). As an immediate fix, replace the current Copy/AssignHead usage with AssignedHead(deep_copy(original.GetHead())). For debugging, print node addresses or run under Valgrind/Dr. Memory to confirm nodes are distinct and to spot double deletes. This will prevent the destructor-triggered assertion and make the class safe to copy and destroy.

Recommended Answers

All 3 Replies

while(head) - why???
you need only:

list::~list() {
	node* current = head->next;
	delete head;
	head = current;
}

The problem, while exhibiting itself when the destructor is called, is not actually in the destructor. Your Copy function makes a shallow copy - in your code object "a" points to the same memory as object "integer". When the first of those gets destroyed at program exit, the pointed to memory of head gets deleted. When the second one is passed to the destructor, it head still has that memory address, but there is no "next" member. So an invalid address is assigned to current, and then to head, and that fails when you try to access the next member of that nonexistent object.

oh i under stood, thanks a lot, i made 2 pointers pointing to the same object at the same time, so redeleting is for sure, thanks a lot again.. Need to fix the Copy function :)

@ ivailosp: oh i want the destructor to delete every element inside the linked list, if i take ur code, it may delete only the beginning :-?

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.