未初始化指针是否持有无效(bogus)地址?CS50内存章节相关疑问
关于你问的几个问题逐一解释:
- 首先明确C语言的基础规则:函数内部声明的非静态局部变量,不会被自动初始化,你声明变量时拿到的内存空间里残留的是什么值,这个变量的初始值就是什么,指针变量也不例外。
- 指针的本质就是存内存地址的整数类型,不管它存的值是你主动分配的合法地址,还是残留的垃圾值,只要你用解引用操作去访问它,C语言都会把它当前存储的数值当成内存地址处理。
- 你问的「无效地址(bogus address)」就是指不符合下面任意一个条件的地址:
- 属于当前运行程序的可访问内存范围
- 你对该地址有对应的读写权限
常见的无效地址包括操作系统内核占用的地址、其他进程的内存地址、程序只读的代码段地址、已经被free释放的内存地址等。
- 回到你贴的代码示例:
int main(void) { int *x; int *y; x = malloc(sizeof(int)); *x = 42; *y = 13; }
x在声明后通过malloc申请了一块int大小的内存,把这块内存的合法地址赋值给了x,所以*x = 42是合法操作。而y声明后没有做任何赋值,它存的就是内存里残留的垃圾值,这个值本身只是一串随机的二进制数据,但因为它存在指针变量里,你做*y = 13操作时,系统就会把这个垃圾值当成内存地址,尝试往这个地址写入13,99%的情况下这个地址都是无效的,轻则触发段错误直接崩溃,重则不小心修改了程序里其他合法变量的值,出现完全不可预知的异常行为,也就是C语言里的「未定义行为」。
- 你最后疑惑的「为什么遗留数据会是一个地址」本质是理解偏差:遗留数据本身不是专门的地址,它只是内存里之前别的操作留下来的随机数值,只是因为你把它存在了指针类型的变量里,用指针的操作逻辑去处理它,它才会被当成地址使用。
内容的提问来源于stack exchange,提问作者random8mile
相关产品推荐
相关产品推荐

