常量引用、非常量引用、临时对象

转载自:https://www.cnblogs.com/littleant/archive/2012/08/01/2618846.html
https://www.cnblogs.com/BensonLaur/p/5234555.html
https://blog.csdn.net/hy13684802853/article/details/87251736

产生临时对象的情况

1.按值进行函数参数传递时
2.函数返回对象时
3.发生类型转化时,例如为了使函数成功调用而进行隐式类型转换

C++中产生的临时对象是不可修改的,及默认为const的,非常量引用的初始值必须是左值,非const引用只能绑定到与该引用同类型的对象,而const引用则可以绑定到不同的但相关的对象或绑定到右值(隐式转化),因为如果将const引用绑定到不同类型的对象(前提是被引用的类型可以转化为引用的类型),会生成一个临时对象,绑定的对象其实是这个临时对象,对这个临时对象操作并不会影响到被引用的对象,所以c++一般规定编译器自行构造的临时对象都是const的,这个也是c++禁止为非常量引用生成临时对象的原因。

const int & i = 3.14;
//实际过程如下
const int temp(3.14);
const int &i = temp;

C++标准的规定:非常量的引用不能指向临时对象

void conv(string &str) { }
int main() 
{
    conv("dasd"); // 这里错了,编译器自动生成一个string(“dasd”)临时对象,不能将该临时对象传给非const引用
}

这里将临时对象赋给了非常量引用,会报错提示非常量限定

       以C++的语义来说,如果一个程序员只想传递参数给函数,而不希望函数修改传入的参数时,那么,或者使用值传递,或者采用常量型引用(const &)。考虑到大对象复制时产生的开销,一般使用常量型引用const &。如果函数的参数是某个类型的一个非常量的引用,那就相当于告诉编译器,程序员希望得到函数对参数的修改结果。
       临时变量是由编译器生成的,C++语言规范没规定编译器生成临时变量的规则,程序员无法得知由编译器生成的临时变量的名字,程序员无法访问那个临时变量。这意味着,以引用的方式传递一个临时变量做为函数参数,如果函数内部对此临时变量做了修改,那么函数返回后,程序员无法获得函数对临时变量的修改。函数对临时变量所做出的所有更改,都将丢失。一方面,在函数申明中,使用非常量型的引用告诉编译器你需要得到函数对某个对象的修改结果,可是你自己又不给变量起名字,直接丢弃了函数的修改结果,编译器只能说:“大哥,你这是干啥呢,告诉我把结果给你,等我把结果给你了,你又直接给扔了,你这不是在玩我吗?同时,C++的标准为了防止给常量或临时变量(只有瞬间的生命周期)赋值(易产生bug),只许使用const引用之。

因此conv函数可以改为:

void conv(string str) { } // 值传递

void conv(const string &str) { } // const引用,因为标准规定临时对象是不能更改的,所以要加上const修饰。

关于临时对象的总结

临时对象是有开销的,所以你应该尽可能的去除它们,然而更重要的是训练自己寻找可能建立临时对象的地方。
1.在任何时候只要见到常量引用(reference to const)参数,就存在建立临时对象而绑定在参数上的可能性。
2.在任何时候只要见到返回对象,就会有一个临时对象被建立(以后被释放)

 

 

 

  • 6
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值