zoukankan      html  css  js  c++  java
  • [转] C++临时变量的生命周期

    http://www.cnblogs.com/catch/p/3251937.html

    C++中的临时变量指的是那些由编译器根据需要在栈上产生的,没有名字的变量。

    主要的用途主要有两类:

    1) 函数的返回值, 如:

    复制代码
     1 string proc()
     2 
     3 {
     4 
     5     return string("abc");
     6 
     7 }
     8 
     9 
    10 
    11 int main()
    12 
    13 {
    14 
    15     proc();
    16     return 0;
    17 
    18 }
    复制代码

    其中第15行会产生一个临时变量。但并不是所有返回值都会创建临时变量,只有当没有将返回值赋值给其它变量时,临时变量才会创建。

    这种临时变量的生命周期很短,当表达式完成后,它就会被销毁了。例如上面的代码,15行产生的临时变量,16行的时候就已经销毁了。

    2) 类型转换时的中间变量。

    1 int a = 3;
    2 
    3 float k = 2.0;
    4 float f = k + a;

    第4行,k+a 由于是 float + int , int 会被转换成 float 再与 k 相加,这个时候就会生产一个临时变量。上面的例子是 build-in type,但对于自定义的类也是同样适用的。

    一般来说,C++ 中的临时变量在表达式结束之后 (full expression) 就被会销毁,比如前面举的两个栗子,但也有例外的时候,如果这个临时变量被用来初始化一个引用的话,那这个临时变量的生命周期就会被延长,直到引用被销 毁,从而不会因此产生悬空(dangling)的引用。

    复制代码
     1 string Proc()
     2 {
     3      return string("abc");
     4 }
     5  
     6 int main()
     7  {
     8      const string& ref = Proc();
     9      cout << ref << endl;
    10      return 0;
    11  }
    复制代码

    如上,第8行产生的临时变量因为有ref指向,它的生命周期会延长至直到main()返回。

    这个特性有时很有用,比如,你可以用一个基类的引用指向一个子类的临时变量,然后通过这个引用来实现多态,但又不用处理子类的销毁。

    复制代码
     1 Class Base()
     2 {
     3     public:
     4       
     5          virtual Bar() { cout << "base bar()" << endl; }
     6 };
     7 
     8 Class DerOne: public Base
     9 {
    10     public:
    11     
    12        virtual Bar() { cout << "DerOne Bar()" << endl; }
    13 };
    14 
    15 class DerTwo: public Base
    16 {
    17     public:
    18        
    19        virtual Bar() { cout << "DerTwo Bar()" << endl; }
    20 };
    21 
    22 
    23 Base GetBase()
    24 {
    25     return Base();
    26 }
    27 
    28 DerOne GetDerOne()
    29 {
    30      return DerOne();
    31 }
    32 
    33 DerTwo GetDerTwo()
    34 {
    35      return DerTwo();
    36 }
    37 
    38 
    39 int main()
    40 {
    41     const Base& ref1 = GetBase();
    42     const Base& ref2 = GetDerOne();
    43     const Base& ref3 = GetDerTwo();
    44 
    45     ref1.Bar();
    46     ref2.Bar();
    47     ref3.Bar();
    48   
    49     return 0;
    50 }
    复制代码

    该小技巧在 Loki::ScopeGuard 的实现中被用到了,使得在一个域内使用多态时,可以避免使用指针,这个写法是这样的巧妙以致被 Andrei 称为:"The Most Important const"。不过需要注意的是,临时变量只能通过 const 引用来指向,因此是不可修改的。

  • 相关阅读:
    gain 基尼系数
    luogu P5826 【模板】子序列自动机 主席树 vector 二分
    牛客挑战赛39 树与异或 离线 树上莫队 树状数组 约数
    4.22 省选模拟赛 三元组 manacher 回文自动机
    4.22 省选模拟赛 最优价值 网络流 最大权闭合子图
    4.18 省选模拟赛 消息传递 树剖 倍增 线段树维护等比数列
    luogu P4008 [NOI2003]文本编辑器 splay 块状链表
    牛客挑战赛39 密码系统 后缀数组
    luogu P1526 [NOI2003]智破连环阵 搜索+最大匹配+剪枝
    luogu P4095 [HEOI2013]Eden 的新背包问题 多重背包 背包的合并
  • 原文地址:https://www.cnblogs.com/qiangxia/p/4277353.html
Copyright © 2011-2022 走看看