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

C语言函数参数、指针参数本质及与&取地址符相关疑问咨询

C语言函数参数的本质属性
  • 函数形参是真实存在的独立局部变量,不是语法层面的虚拟占位符。函数被调用时,系统会在当前函数的栈帧空间内,为每一个形参分配专属的内存区域,它的生命周期、内存管理逻辑和函数内部手动定义的普通局部变量完全一致:函数进入执行流时分配内存,函数返回后随栈帧销毁一同被回收。
  • 不存在“形参是专门用来存储其他变量的特殊变量”的模糊定义,它的核心属性是C语言值传递机制下的拷贝接收载体:函数调用发生时,传入的实参会先完成一次值拷贝,拷贝出的副本会被写入形参对应的内存空间,后续函数内部对形参的所有读写操作,都只作用在这块独立的内存上,默认无法直接修改调用方持有的原始实参。

注意不要把C语言的形参规则和C++的引用形参混淆:C语言原生没有引用语义,所有参数传递统一走值拷贝逻辑,形参永远是独立的实体,不会和外部变量绑定为别名。

指针参数的核心规则答疑

为什么传参时已经用&拿到了内存地址,函数定义阶段仍需要声明指针类型形参?

&运算符取到的结果本质是一个代表内存地址的整数值,但C语言是强类型静态语言,所有变量必须明确声明类型,指针类型的标记有两个不可替代的作用:

  • 给编译器传递合法语义标记:只有当形参被声明为指针类型时,编译器才会认可对该变量做*解引用操作是合法语法;如果把存地址的形参声明为普通整型,后续写解引用逻辑会直接触发编译报错。
  • 明确内存访问的规则:指针类型携带了它指向的目标的数据类型信息,编译器会根据这个信息确定解引用时的访问步长、数据解析规则。比如形参声明为int*时,解引用会从存储的地址开始读取对应int长度的字节,把内容解析为整型;如果错声明为char*,解引用只会读取1个字节,最终得到的数据会完全错误。

指针参数是否确实用于存储内存地址?

  • 是,但指针参数本质没有任何特殊性,它就是一个类型为指针的普通局部变量,只是存储的数值被约定为「某块内存的地址」而已。
  • 传参时传入&变量的逻辑,和传普通整型值没有本质区别:都是把实参的值做一次拷贝,写入形参的内存空间。这也是为什么在函数内部直接给指针形参本身赋值(比如写p = NULL),只会修改形参这个局部变量自己存储的地址值,完全影响不到外部变量;只有通过*p的方式解引用,顺着形参里存储的地址找到对应的外部内存空间,才能修改外部变量的值——这就是“指针可以修改函数外变量”的本质,不存在什么特殊的跨作用域魔法。

可以配合一段简单的代码验证逻辑:

#include <stdio.h>

void demo(int normal_arg, int *ptr_arg) {
    // 两个形参都是demo函数栈帧内的独立局部变量
    normal_arg = 999; // 仅修改局部的normal_arg,外部实参不受影响
    *ptr_arg = 888;  // 顺着ptr_arg存的地址,修改外部变量的内存内容
    ptr_arg = NULL;  // 仅修改局部的ptr_arg存储的地址值,外部指针不受影响
}

int main() {
    int num1 = 10;
    int num2 = 20;
    demo(num1, &num2);
    // 输出结果为 num1 = 10, num2 = 888
    printf("num1 = %d, num2 = %d\n", num1, num2);
    return 0;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.27 06:03:12