You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言实现链表ADT报Segmentation fault (core dumped)错误如何解决

问题定位
  • 核心触发点是空指针解引用:init函数执行后,链表的head指针被赋值为NULL,同时length被设置为10。调用print函数时,循环第一次执行就会对空指针p(初始值等于head也就是NULL)执行(*p).num操作,访问非法内存直接触发段错误。
  • 逻辑设计错误:List结构体的length字段被用作最大容量,但没有额外字段记录当前链表实际存储的节点数,空链表无任何节点的情况下,print函数强制遍历length次,完全不符合链表实际状态。
  • 遍历逻辑漏洞:print函数没有对遍历指针做非空判断就直接解引用,哪怕后续插入了部分节点,只要实际节点数小于length,依然会触发空指针访问。
修复方案

快速临时修复(仅避免段错误,不调整整体逻辑)

直接修改print函数的循环判断条件,增加指针非空校验:

void print(List L) {
 int i; 
 NodeType *p;

 printf("List is: ");
 for (i=0, p=L.head; i<L.length && p != NULL; i++, p=p->next) { // 增加p != NULL判断
   printf(" %d ", p->num);
 }
 putchar('\n');
}

修改后空链表调用print会直接输出List is: ,不会触发崩溃。

规范修复(调整链表ADT逻辑)

  1. 修改list.h中的List结构体定义,区分最大容量和实际节点计数:
typedef struct {
  int max_size; // 存储链表最大容量
  int cur_size; // 存储当前实际存储的节点数
  NodeType *head;
} List;

// 补充add函数声明
void add(List *L, int val);
  1. 修改list.c中的init函数初始化逻辑:
void init(int maxSize, List *L) {
   L->max_size = maxSize;
   L->cur_size = 0; // 初始无节点,实际计数为0
   L->head = NULL;
}
  1. 修复print函数的遍历逻辑,直接以指针非空作为遍历终止条件:
void print(List L) {
 NodeType *p = L.head;
 printf("List is: ");
 while (p != NULL) {
   printf(" %d ", p->num);
   p = p->next;
 }
 putchar('\n');
}
  1. 补充实现add插入函数,插入时更新实际节点计数:
void add(List *L, int val) {
  // 容量判断
  if (L->cur_size >= L->max_size) {
    printf("链表已达最大容量,插入失败\n");
    return;
  }
  // 申请新节点内存
  NodeType *new_node = (NodeType*)malloc(sizeof(NodeType));
  if (new_node == NULL) {
    printf("内存申请失败\n");
    return;
  }
  new_node->num = val;
  // 头插法插入节点,可根据需要改为尾插
  new_node->next = L->head;
  L->head = new_node;
  L->cur_size++;
}

修改后放开main函数中add调用的注释即可正常插入、遍历链表。

内容的提问来源于stack exchange,提问作者Cheetos

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.24 19:06:09