2015-09-27 56 views
2

在下面的代码片段中,至少只要它与<<运算符一起使用,是否可以安全地将Quote::toXML返回的临时字符串的引用存储在ToXML::s_成员变量中?即是子表达式q.toXML直到下一个;的结果?另一个C++临时生命周期混淆

什么是这里完整的表达w.r.t.返回值为q.toXML。整个std::cout或致电ToXML的构造函数?

#include <iostream> 
#include <string> 

struct ToXML 
{ 
    ToXML(char const * const tag, std::string const & s) : tag_(tag), s_(s) 
    { 
    } 

    char const * tag_; 
    std::string const & s_; 
}; 

std::ostream & operator << (std::ostream & os, ToXML const & v) 
{ 
    return os << "<" << v.tag_ << ">" << v.s_ << "</" << v.tag_ << ">"; 
} 

struct Quote 
{ 
    std::string toXML() const 
    { 
     return "<Quote/>"; 
    } 
}; 

int main() 
{ 
    Quote q; 
    std::cout << ToXML("quote", q.toXML()) << std::endl; 
    return 0; 
} 
+0

看看:http://stackoverflow.com/questions/2822243/store-return-value-of-function-in-reference-c 根据这些信息,由于你的函数采用const引用它看起来OK 。 –

回答

2

是的,它是安全的。

从[class.temp]:

存在其中的临时被在不同的点比全表达式的结尾破坏两个上下文。

第二个上下文是当引用绑定到一个临时对象时。引用绑定的临时对象或引用绑定到的子对象的完整对象的临时对象仍然存在 参考的生命周期除外:
- 在函数调用(5.2.2)中绑定到参考参数的临时对象一直存在,直到完成包含调用的完整表达式 。

我们在这一点上。临时对象绑定到引用参数(s)并一直持续到包含该调用的完整表达式的完成。也就是说,它一直存在,直到

std::cout << ToXML("quote", q.toXML()) << std::endl; 
// --- here ---------------------------------------^ 

因为它在整个使用过程中持续,所以它是完全安全的。然而,只要你做这样的事情:

ToXML x("quote", q.toXML()); 

你坚持悬挂参考,所以我会谨慎使用这种模式。