相信你遇到过指针传参、值传参、引用传参,这三个关系足够让你头脑爆炸,搞不清楚三者的区别。但是恭喜你,你看到了这篇文章,小编保证你看后茅塞顿开,一下子就顺畅了。

首先,我们要先知道什么是指针,是的,指针是C/C++独有的特色,并且它的指针还不会自动释放,不像Java、python那样的自动回收机制,所以还是需要程序员自己释放它。举个例子就是:你在饭堂吃饭,向饭堂申请了一个饭盒,然后装饭装菜,吃完饭,你要自己把饭盒拿到回收站,不然你就会被别人指指点点。

很多童鞋一看到指针就浑身发抖,因为你怕他指来指去的,不知道知道哪去了。其实不用它,你越怕它,它就越 “锋利”。其实指针也是一个变量,只不过这个变量的值存放了地址。

所以知道了指针,我们来看一下函数参数的指针传递和引用传递。

函数的参数是称之为形参,然后调用函数的参数叫做实参。指针传递其实就是开了指向要改变的值的形参,我们来看指针传递的几种情况吧:

一、指针传递

1. 指针传递改变单一变量值

将指针作为函数的参数,然后再调用该函数的时候将变量进行取址符号传递给指针。

/*值传递函数,这里形参改变,实参是没有变化的*/voidTest_1(inta){  a = 2;}/*指针传递函数,这里形参改变,实参会跟着变化的*/voidTest_2(int*a){  *a = 2;}intmain(){int i = 1;Test_1(i);Test_2(&i);//把i的地址传递给参数a指针的指向return 0;  }

2. 指针传递改变指针变量的值

下面的代码是为指针变量分配一个随机地址

指针也是一个变量,只不过这个变量中存的值是一个地址

void Test_1(int **p){*a=(int*)malloc(sizeof(int *));//这里的*a的含义是指向指针的指针的值}intmain(){  int *a;  // 定义一个指针变量Test_1(&a);//取出指针变量的地址(也就是存放指针a的地址)//括号里面不能写*a,因为此时定义的*a还没有指向,所以直接用*a会导致内存泄露  return 0;  }

3. 改变数组的值

数组的名字就是对应了它的首地址

voidTest(int*a){  a[0] = 2;a[1] = 3;a[2]=4;}intmain(){  int a[3] = {0,1,2};  Test(a);              // 数组的名称就是地址了  return 0;  }

总结:指针传递其实就是开多了一个指针形参指向要改变的值的地址(只不过是不同时候要改变对象的类型不同),进而在调用函数中改变固定地址中的值。

二、引用传递

1. 引用传递单一变量值

voidTest(int&a){  a = 2;}intmain(){int a = 1;Test(a);//直接将a传过去,不用取地址操作,就是直接实参去改变,没有形参之说  return 0;  }

2. 改变指针变量​

下面代码为指针随机分配了一个地址(指针变量的值就是地址)

voidTest(int*&a){//引用传递变量名前面的类型与传入的变量一致a=(int*)malloc(sizeof(int *))}int main(){int*a;//定义了一个int指针类型的变量Test(a);return0;}

3. 改变数组的值

voidTest(int(&a)[3]){//数组的传递方式除了&数组名之外还要指出其长度a[0] = 2;a[1] = 3;a[2]=4;}int main(){  int a[3]={0,1,2};Test(a);//直接传递数组名return 0;  }

4.引用传递动态开辟空间

用完free掉空间,这里先省略这个步骤

#define len 3void Test(int* &a){  a=(int*)malloc(len*sizeof(int *));//动态开len长度空间;   a[0]=1;  a[1]=2;  a[2]=3; } int main(){int*a;Test(a);  return 0;}

​总结:引用传递其实就是相当于直接把那个实参本身传过去,改的就是那个实对应的值,省去了开形参的步骤,也能提高效率,​而且还不会被指针弄晕。

欢迎大家关注小编的公众号 “三贝勒文子”呀~~​,每天更新关于C++和C的知识点。

参考:C/C++指针传递,引用传递(多个例子助理解)_Mr.琛的博客-CSDN博客_c++ 指针传递