【发布时间】:2019-06-03 04:48:10
【问题描述】:
所以我正在尝试创建一个 XOR 双链表作为练习的一部分,但我的 removeFirst() 函数不断出现分段错误。我无法弄清楚出了什么问题,有人有线索吗?
这是一个节点的样子:
class Node{
public:
int data;
Node *XOR;
};
我正在使用这个函数来计算异或:
Node* returnXOR(Node *a, Node *b){
return (Node*)((uintptr_t) (a) ^ (uintptr_t) (b));
}
这是我的 XOR 双向链表类:
class XORDLL{
public:
Node *head;
XORDLL(){
head = NULL;
}
void addFirst(int data){
// Make a newNode pointer
Node *newNode = new Node;
// Set the variables
newNode->data = data;
newNode->XOR = returnXOR(head, NULL);
// If the head is not empty set the XOR of the head to the next XOR the newNode
if(head != NULL){
head->XOR = returnXOR(newNode, returnXOR(head->XOR, NULL));
}
// Set the newNode to the head
head = newNode;
}
void removeFirst(){
// If head is equal to NULL, do nothing
if(head == NULL){
return;
}
// Store current head
Node *tmp = head;
// Set head equal to the next address
head = returnXOR(tmp->XOR, NULL);
head->XOR = returnXOR(tmp->XOR, tmp);
// Delete tmp variable
delete tmp;
}
void printList(){
Node *current = head;
Node *prev = NULL;
Node *next;
while(current != NULL){
printf("%d ", current->data);
next = returnXOR(current->XOR, prev);
prev = current;
current = next;
}
printf("\n");
}
};
当我运行这段代码时:
int main(){
XORDLL l;
l.addFirst(1);
l.addFirst(2);
l.addFirst(3);
l.printList();
l.removeFirst();
l.printList();
return 0;
}
这是输出:
3 2 1 分段错误(核心转储)
【问题讨论】:
-
你的
returnXOR函数获取两个现有Nodes 的原始内存地址,对这两个原始内存地址进行异或,并将结果转换为指向另一个Node的指针。不幸的是,生成的内存地址是指向Node的有效指针的实际机会微乎其微。因此你的崩溃。这就像在非洲沙漠中获取两个绿洲的地理经度和纬度,不包括经度/纬度或数字经度/纬度,前往新的坐标集,并期望在那里找到第三个绿洲。 -
我也是这么想的,但是为什么我的 printList() 函数在使用相同的方法时可以正常工作。
-
因为,如果您计算出数学,该代码总是最终访问两个有效节点,然后计算一个 NULL 值(第一个与 null 异或,与 0 异或,什么都不做;下一次迭代异或自身的内存地址,产生 NULL)。你在那里很幸运。顺便说一句,
delete current, prev, next;并没有按照你的想法去做。我重复一遍,它不会删除三个指针。看来spend a little bit more time reading a good C++ book是个好主意。 -
感谢您提供的信息,我必须自己解决。
-
@JornvanderMaat
Node *newNode = (Node*) malloc (sizeof(Node));-- 你为什么在 C++ 程序中使用malloc?该代码表现出未定义的行为,因为Node不是 POD 类型。您的代码不构造Node对象——在 C++ 中,operator new用于动态构造类型。malloc所做的只是分配字节——它不构造对象。
标签: c++ data-structures doubly-linked-list