什么时候创建作为一个函数调用的一部分被创建? [英] When are temporaries created as part of a function call destroyed?
问题描述
作为函数调用的参数的一部分而临时创建的函数调用是否保证在调用函数结束之前停留,即使临时函数未直接传递给函数?
Is a temporary created as part of an argument to a function call guaranteed to stay around until the called function ends, even if the temporary isn't passed directly to the function?
几乎没有机会一致,所以这里有一个例子:
There's virtually no chance that was coherent, so here's an example:
class A {
public:
A(int x) : x(x) {printf("Constructed A(%d)\n", x);}
~A() {printf("Destroyed A\n");}
int x;
int* y() {return &x;}
};
void foo(int* bar) {
printf("foo(): %d\n", *bar);
}
int main(int argc, char** argv) {
foo(A(4).y());
}
如果 A(4)
直接传递给 foo
,它肯定不会被销毁,直到 foo
调用结束, m调用临时的方法并失去对它的任何引用。我本能地认为临时 A
将在 foo
甚至开始之前被销毁,但是使用GCC 4.3.4测试显示它不是;输出为:
If A(4)
were passed directly to foo
it would definitely not be destroyed until after the foo
call ended, but instead I'm calling a method on the temporary and losing any reference to it. I would instinctively think the temporary A
would be destroyed before foo
even starts, but testing with GCC 4.3.4 shows it isn't; the output is:
构造A(4)
foo():4
销毁A
Constructed A(4)
foo(): 4
Destroyed A
问题是是GCC的行为是否符合规范或者是一个编译器允许在调用 foo
之前销毁临时 A
,无效的指向其成员I' m使用?
The question is, is GCC's behavior guaranteed by the spec? Or is a compiler allowed to destroy the temporary A
before the call to foo
, invaliding the pointer to its member I'm using?
推荐答案
临时对象存在,直到创建它们的完整表达式的结尾。
Temporary objects exist up until the end of the full expression in which they are created.
在您的示例中,由 A(4)$创建的
A
c $ c>将至少存在 ,直到表达式从调用 foo()
返回后结束。
In your example, the A
object created by A(4)
will exist at least until the expression ends just after the return from the call to foo()
.
这种行为由语言标准保证:
This behavior is guaranteed by the language standard:
临时对象作为评估的最后一步被销毁包含它们创建点的全表达式(1.9)(词法)。即使评估结束于抛出异常(C ++ 03§12.2/ 3),也是如此。
Temporary objects are destroyed as the last step in evaluating the full-expression (1.9) that (lexically) contains the point where they were created. This is true even if that evaluation ends in throwing an exception (C++03 §12.2/3).
临时可以通过绑定对它的引用来扩展(在这种情况下,它的生存期被延长,直到引用的生命周期结束),或者通过将其用作构造函数的初始化器列表中的初始化器(在这种情况下,正在构造的对象是完全构造的)。
The lifetime of the temporary may be extended by binding a reference to it (in which case its lifetime is extended until the end of the lifetime of the reference), or by using it as an initializer in a constructor's initializer list (in which case its lifetime is extended until the object being constructed is fully constructed).
这篇关于什么时候创建作为一个函数调用的一部分被创建?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!