c++之引用

概念:

引用是给变量另外去一个别名,就类似于一个人有大名也有小名一样,别名不会另外开辟空间,和原来的变量名共用一块内存空间

使用方法:

类型&引用变量名=引用实体

int main()
{
	int a = 10;
	int& b = a;
	cout << a << endl << b << endl;
	cout << &a << endl << &b << endl;
	return 0;
}

b是a的别名,当打印a和b的地址时,是同一个地址 

注意:1.引用的类型必须和引用实体类型一致

           2.引用在定义时必须初始化,是谁的别名

           3.一个变量可以用多个引用,像a的别名可以时b,也可以是c等等

           4.引用一旦引用了一个实体,就不能在引用其他实体

int a=10;
int c=20;
int&b=a;
b=c;

这里就很好的解释了第四条注意事项,当引用了一个实体后不能在引用其他实体,b=c,b是a的别名,a和b都变成了20,这里不是把b变成c的引用

常引用:

int main()
{
	int a = 10;
	const int& b = a;
	b = 20;
	const int c = 10;
	int& d = c;
	return 0;
}

1.当实体没有被const修饰时,引用被const修饰时,b=20会编译错误

2.当实体被const修饰时,引用没有被const修饰时,int&d=c会编译错误

总结:这是权限的缩小还是放大问题,实体可读可改,那引用就无所谓,当实体只能读不能改时(也就是被const修饰,只能读这个变量,不能修改里面的值)那引用只有加上const才行,不然实体只能读,而我可以通过别名去修改就说不过去了,这也就是权限的放大,权限缩小是可以的,也就是当一个实体可读可改,别名只能读,这是被允许的

int main()
{
	int a = 10;
	int& b = a;
	double& c = a;
	const double& d = a;

}

这里除了第三条都可以编译过去,第三条违反的原则是引用的实体必须和引用类型一样

第二条很明显也能编译过去,第四条在这里需要重点注意

需要明确的一点是,临时变量具有常性,这里会先生成一个临时变量,10变成10.0(类型转换,int->double)然后在d在绑定到这个临时变量身上,因为是const才可以绑定,临时变量具有常性,没有const修饰就不合法,输出是10,因为cout默认省略掉后面的0

可以通过cout<<&d和&a明显看出不是同一个地址

 使用场景:

1.做参数(有点类似于指针)

void swap(int& a, int& b)
{
	int temp = a;
	a = b;
	b = temp;
}
int main()
{
	int a = 10;
	int b = 20;
	swap(a, b);
	cout << a << endl;
	cout << b << endl;
	return 0;
}

这里a和b是别名,形参是实参的别名

2.做返回值

int test1()
{
  static int n=0;
  n++;
  return n;
}
int& test2()
{static int n=0;
  n++;
  rteturn n;
}

在test1中是平时使用的函数返回,值返回,这里会创建一个临时变量,类型是int,然后在给外面,假设临时变量叫temp,这句话就相当于int temp=n;创建一个临时变量,要开空间,这个临时对象会在函数返回时生成,并且在调用者使用完返回值之后被销毁。

在test2中使用引用返回,避免了创建临时变量,不会开临时空间,就类似int&temp=n;

int&r1=test1();
int&r2=test2();

第一个不允许,也就是违背了常引用里的第四条,因为传值返回会创建一个临时变量,r1没有const修饰,所以第一个编译不过去

第二个没有创建临时变量,没有开辟空间,是允许的。

那为什么函数体内要有static修饰呢?

无论函数传值返回还是参数传值,都会拷贝,传引用就不会,就会返回n,但引用返回时,必须指向一个函数调用结束后仍然有效的对象,也就是static修饰的变量,被放在了静态区,否则出了函数n被销毁了,那int&temp=n;会指向一个被销毁的对象,会导致未定义行为,这也间接的说明了引用返回不安全,得谨慎使用

引用和指针的区别:

1.引用在定义时必须初始化,指针没有要求int*p=NULL;

2.引用在引用一个实体后不能改变,指针可以随时指向别的实体(变量)

3.sizeof不同,引用是看引用实体的类型,指针是看32位还是64位机器

4.有多级指针int*,int**,没有多级引用

总结:

引用可以提高传参时的效率,避免创建临时空间,效率高。但实际使用场景得谨慎

引用的底层逻辑是使用指针实现。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值