我做到了:
class Node {
//
int key;
Node* next;
public:
//
Node() : key( -1 ), next( NULL ) {}
Node( int i, Node* j ) : key( i ), next( j ) {}
//
~Node() { delete next; }
//
static void head_insertion( Node* & head, int i );
void print_list();
};
void Node::head_insertion( Node* & head, int i ) {
cout << "insert() 1 head = " << head << endl;
// append the current list to n
Node n(i, head);
cout << "address of n = " << &n << endl;
// make n the new head
head = &n;
//
cout << "insert() 2 head = " << head << endl;
}
头部插入不起作用:
insert() 1 head = 0x7fff56821518
address of n = 0x7fff56821518
insert() 2 head = 0x7fff56821518
Segmentation fault: 11
我有两个问题:
n
中新创建的节点head_insertion
与head
指向的地址具有相同的地址。发生了什么事?答案 0 :(得分:1)
您没有使用动态内存来分配n
。在第一次传递时,它会被添加到列表中,然后函数结束并且n
超出范围。在第二遍时,它碰巧出现在堆栈上的相同位置,产生相同的指针
答案 1 :(得分:0)
在函数void Node::head_insertion( Node* & head, int i )
中,您正在创建一个自动变量Node n()
,其生命周期在函数范围内。因此,如果要访问该节点,head_insertion
函数之外将获得segmentation fault
函数{ {1}}因为您不再拥有该内存区域。
为了防止您动态创建对象:
Node* n = new Node(i,head)
关于您的上一个问题:即使您不编写自己的析构函数,编译器也会为您提供默认版本。我猜析构造函数不会调用destractor,所以为什么要递归。
答案 2 :(得分:0)
void Node::head_insertion( Node* & head, int i )
中的代码:
Node n(i, head);
cout << "address of n = " << &n << endl;
// make n the new head
head = &n;
应该是:
Node *pn = new Node(i, head);
cout << "address of n = " << pn << endl;
// make n the new head
head = pn;
析构函数~Node() { delete next; }
导致链接断开,应该避免。
还有更多...... 整个设计造成了问题。
您的类实现节点是什么,Node应该做什么。
class Node {
int key;
Node* next;
public:
Node() : key( -1 ), next( NULL ) {}
Node( int i, Node* j ) : key( i ), next( j ) {}
//
~Node() { } // don't delete the next node here! Not the job of this object.
void print_node();
};
class Linklist {
Node *head;
public:
Linklist(): head(0) {}
static void head_insertion( Linklist & list, int i );
void print_list();
〜Linklist(); // traverse your list node and do the deletion here
}
将列表级别的事情放在按类链接列表处理。