C ++:临时参数的寿命?
当创build一个MyClass
的新实例作为一个像这样的函数的参数:
class MyClass { MyClass(int a); }; myFunction(MyClass(42));
这个标准是否使得任何受害者的parsing器的时间?
具体来说,我可以假设它会在调用myFunction()
之后的下一个语句之前被调用吗?
临时对象在它们所属的完整expression式的末尾被销毁。
完整expression式是不是其他expression式的子expression式的expression式。 通常这意味着它结束于;
(或)
if
, while
, switch
等)表示语句结束。 在你的例子中,这是函数调用的结束。
请注意,可以通过将临时对象绑定到一个const
引用来延长临时对象的生命周期。 这样做延长了他们的生命到参考的一生:
MyClass getMyClass(); { const MyClass& r = getMyClass(); // full expression ends here ... } // object returned by getMyClass() is destroyed here
如果您不打算更改返回的对象,那么在未应用返回值优化的情况下,这是保存复制构造函数调用的一个很好的技巧(与MyClass obj = getMyClass();
)相比较。 不幸的是,它不是很知名。 (我想C ++ 11的移动语义将使其不那么有用,但是)。
每个人都正确地引用了12.2 / 3或类似的,这回答你的问题:
临时对象作为评估完整expression式(词法)包含创build点的最后一步被破坏。
我发现在我的标准打印的下一页上 ,12.2 / 4说:
有两种情况下临时销毁在不同于完整expression式结束的点上。
它们都不适用于你的例子,它们都涉及在初始化器中使用临时对象。 但是它的确表明,在处理像C ++标准这样的棘手的野兽时,你必须保持清醒的头脑。
该标准确实提供了保证 – 从第12.2 / 5节:
在函数调用(5.2.2)中引用参数的临时绑定一直存在,直到完成包含调用的完整expression式
然而,在你的代码中,不清楚参数是通过引用还是通过值来传递的,尽pipe在某些时候将会使用一个引用的拷贝构造函数。
ANSI / ISO C标准第12.2节“临时对象”第3节规定:“…临时对象作为评估完整expression式的最后一步被破坏(词法上)包含它们被创build的点。
这与序列点的概念密切相关。 当达到一个顺序点时,保证expression式的所有副作用都已经发生。