我正在尝试编写一个函数,从链表中删除给定位置的元素,目前我使用的是一个只有头指针的链表。现在可能是用户输入的位置大于链表的大小,所以为了补救,我写了这样的:
int delete(struct node** head, int pos)
{
struct node* temp = *head;
while(pos!=0 && temp->next!=NULL)
{
temp=temp->next;
pos--;
}
if(pos>0)
return 0;
}
但它给出了以下错误
fish: './a.out' terminated by signal SIGSEGV (Address boundary error)
我试图通过编写一个新的代码来调试它
int delete(struct node** head)
{
if((*head)->next==NULL)
return 1;
}
但它给出了相同的错误
当head
为NULL
时,对temp->next
的评估将给出未定义的行为或您所经历的错误。
然而,您的函数还有更多需要纠正的地方。
-
没有发生删除。若要删除节点,其前置节点的
next
属性应更新为指向已删除节点之后的节点。然后应该释放被删除的节点。 -
删除列表的第一个节点时,应修改
*head
的值。 -
该函数应该返回一个
int
,因此,当删除成功时(以及循环后的pos == 0
(,应该有一个执行的return
,可能返回1表示成功。 -
没问题,但我建议您的函数使用不同的名称。如果您转到C++,那么
delete
将是一个保留字。
所以:
int removeNode(struct node** head, int pos) {
if (*head == NULL) {
return 0;
}
struct node* temp = *head;
if (pos == 0) { // Case where first node must be removed
*head = (*head)->next; // Modify head reference
free(temp);
return 1; // Indicate success
}
while (pos > 1 && temp->next != NULL) {
temp = temp->next;
pos--;
}
if (pos != 1 || temp->next == NULL) {
return 0; // Invalid position
}
// Remove the node
struct node* prev = temp;
temp = temp->next;
prev->next = temp->next;
free(temp);
return 1; // Indicate success
}
如@padid所评论,
我没有考虑头本身指向NULL的情况。
一个简单的if语句解决了
struct node* temp = *head;
if(temp==NULL){
printf("Empty LLn");
free(temp);
return 0;
}