我正在学习如何在 C 中构建链接列表。我的程序编译但由于某种原因我无法弄清楚,我得到分段错误。我一直试图找出问题一段时间,但我没有运气。这是错误的代码:
int len()
{
struct list * current = head;
int length = 0;
while (current != NULL)
{
length++;
current = current -> next; //move to next node
}
return length;
}
struct list * search ( int key)
{
struct list * current = head;
while (current != NULL && current->data != key)
current = current -> next;
if (current != NULL && current -> data == key)
return current;
return NULL;
}
/* Insert a new data element with key d into the end of the list. */
void insert(int d ) // at the end
{
struct list * current = head;
struct list * new;
while (current -> next != NULL)
current = current -> next;
new = (struct list *)malloc(sizeof(struct list));
new -> data = d;
current -> next = new;
new -> next = NULL;
}
void insertAfter(int d, int where ) // insert at the middle
{
struct list * marker = head;
struct list * new;
while(marker -> data != where)
marker = marker -> next;
new = (struct list*)malloc(sizeof(struct list));
new -> next = marker -> next;
marker -> next = new;
new -> data = d;
}
/* Remove the node with value d from the list */
/* assume no duplicated keys in the list */
/* If the list is empty, call prtError() to display an error message and return -1. */
void delete(int d)
{
struct list * current1 = head;
struct list * current2;
if (len() == 0)
{ //prtError("empty");
exit(0);
}
if (head -> data == d)
{
head = head -> next;
}
//Check if last node contains element
while (current1->next->next != NULL)
current1 = current1->next;
if(current1->next->data == d)
current1->next == NULL;
current1 = head; //move current1 back to front */
while(current1 -> next -> data != d)
current1 = current1 -> next;
current2 = current1 -> next;
current1 -> next = current2 -> next;
}
我在第一行的删除方法中遇到了分段错误:
while(current1 -> next -> data != d)
为什么这是错的?
答案 0 :(得分:0)
您发布的代码存在许多问题,但您在评论中提到您关注insert()
。它崩溃的原因是,如果调用head
时insert()
为NULL,您将取消引用NULL指针。
当它为NULL时,您需要在head
处插入一个特殊情况:
if (head) {
while (current -> next != NULL)
current = current -> next;
}
new = (struct list *)malloc(sizeof(struct list));
new -> data = d;
if (current) {
current -> next = new;
} else {
head = new;
}
new -> next = NULL;
您应该检查其他功能中的类似问题。使用search()
函数作为避免在循环中取消引用NULL指针的示例。
答案 1 :(得分:0)
您在insert
中有几个问题:
while (current -> next != NULL)
您不会检查current
是否为NULL
。 delete
中存在类似问题:
if (head -> data == d)
您需要在此处查看head
并:
while (current1->next->next != NULL)
也是一个问题。
答案 2 :(得分:0)
插入后出现错误,您将超出列表末尾未找到元素。
答案 3 :(得分:0)
在insert
,
while(current->next != NULL) current = current->next;
这将保证current == NULL
。
current->next = new;
每次都会崩溃。
答案 4 :(得分:0)
也许它在insertAfter
:
while(marker -> data != where)
marker = marker -> next;
如果找不到data == where
的节点,marker
将成为NULL
指针。
稍后在您的代码中取消引用NULL
指针:
new = marker -> next;
它会产生段错误。检查marker->next != NULL
是否应避免:
while(marker->next != NULL && marker -> data != where)
marker = marker -> next;
但是你应该尝试使用调试符号(-g
选项)编译你的程序,并在像GDB这样的调试器中逐行运行。