使用char**指针与strdup函数赋值时触发段错误的原因是什么?
为什么这段代码会触发段错误?
嘿,这个问题我太熟悉了——咱们来一步步拆解问题所在:
核心问题:未初始化的指针p
你写的char **p;只是声明了一个指向字符指针的指针,但它并没有被初始化。这意味着p当前指向的是一块完全随机的内存地址,这块内存要么不属于你的程序,要么是受系统保护的区域,完全没有合法的访问权限。
p[0] = strdup("hello");的实际行为
p[0]在C语言里等价于*(p + 0),也就是尝试去访问p当前指向的内存中的第一个char*位置,然后把strdup返回的堆内存地址赋值给它。但因为p本身没有指向任何合法的内存空间,你本质上是在往一块无效的内存地址写数据——这直接违反了操作系统的内存保护规则,系统必然会触发段错误来终止程序,防止你破坏内存。
怎么修复这个问题?
你需要先让p指向一块合法的内存空间,有两种常见的方式:
- 方式一:在堆上分配内存
如果你需要p作为一个指针数组使用,可以先给它分配至少能容纳一个char*的内存:char **p = malloc(sizeof(char*)); // 分配能存一个char*的堆内存 if (p == NULL) { // 处理内存分配失败的情况 return 1; } p[0] = strdup("hello"); // 用完记得释放内存 free(p[0]); free(p); - 方式二:绑定到栈上的变量
如果你只是需要p指向一个单个的字符指针,可以把它指向一个栈上的char*变量:char *str; char **p = &str; // 让p指向栈上的str变量 p[0] = strdup("hello"); // 用完释放strdup的内存 free(p[0]);
内容的提问来源于stack exchange,提问作者David Roonie




