指针数组能否指向可变长度字符串?以下C代码是否有误请说明原因
C代码问题分析及疑问解答
一、当前启用代码的正确性验证
你贴出的未注释的代码逻辑不存在错误,可以正常运行,相关说明如下:
- 头文件兼容性提示:代码中使用的
#include <malloc.h>属于非标准头文件,标准C规范下使用malloc需要引入#include <stdlib.h>,部分编译器可能无法识别malloc.h导致编译报错。 - 内存分配匹配:
arr[0]分配的3字节内存刚好可以存储字符串"he"(2个可见字符+1个\0结束符,总长度3字节),arr[1]分配的2字节内存刚好可以存储字符串"h"(1个可见字符+1个\0结束符,总长度2字节),两次strcpy操作都不会出现缓冲区越界。 - 运行后会正常输出如下结果:
he h
二、注释代码的错误说明
如果打开注释代码运行,会触发异常,各注释行的问题分别是:
memcpy(*c[2],"hell",sizeof("hell"));- 数组下标越界:你定义的指针数组
arr仅包含2个元素,合法下标范围是0和1,访问c[2]属于越界访问,行为未定义。 - 操作符优先级问题:
[]优先级高于*,*c[2]等价于*(c[2]),在本身越界的前提下,属于对非法内存地址的访问。 - 缓冲区长度不足:
"hell"总长度为5字节(4个可见字符+1个\0结束符),就算目标内存地址合法,也需要至少5字节的存储空间才不会溢出。
- 数组下标越界:你定义的指针数组
c[0]="hello";、c[1]="hi";
这两行语法本身没有问题,但会导致内存泄漏:直接把指针指向字符串常量的地址,会丢失之前malloc返回的堆内存地址,后续没有办法对这部分内存执行free释放。
三、指针数组指向可变长度字符串的说明
指针数组完全可以指向长度可变的字符串:指针数组的每个元素都是char*类型的指针,只要给指针赋值合法的字符串首地址即可,常见使用场景包括:
- 指向堆上动态分配的不同长度内存:可以给
arr[0]重新申请更大的空间存储更长的字符串,也可以释放原有空间后申请更小的空间,长度完全灵活可控。 - 指向不同长度的字符串常量:例如直接定义
char *arr[] = {"hello", "hi", "test1234"},每个元素指向的字符串长度都可以不相同。
额外编码建议
- 实际生产环境中建议对
malloc的返回值做判空处理,避免内存分配失败时访问空指针导致程序崩溃。 - 程序退出前建议主动
free掉malloc申请的堆内存,避免内存泄漏。
内容的提问来源于stack exchange,提问作者user786
相关产品推荐
相关产品推荐

