![]() |
1
10
GCC是对的。 在第二个例子中,我们没有寿命延长,因为 [class.temporary] ¶6.11 :
如果我们这样重写示例:
clause 6.9 反而会起作用:
那么,为什么寿命延长适用于第一个例子?很简单:聚合初始化程序不是函数调用。它们在标准的不同部分进行了描述:函数调用在中进行了描述 [expr.call] ,而初始化表达式在中进行了描述 [expr.type.conv] (和中的聚合初始化 [dcl.init.aggr] ).
但是,请注意,如果
那么调用该构造函数就算作函数调用,此时 [class.temporary] ¶6.9 再次变得相关。 0 如果没有它,就寿命而言,聚合的引用成员将被视为直接声明为变量。 如果你想像Clang(不正确地)那样在没有临时寿命延长的情况下执行聚合初始化,你可以使用括号而不是大括号进行初始化,这将触发 [class.temporary] ¶6.10 :
不幸的是,Clang目前显然没有实现这一点,因为这是C++20的一个新添加(提案 P0960 ). 请注意,该提案的文本甚至明确指出,第一个例子中的GC行为是标准的意图。 0 大概该子句仅提及中所述的函数调用 [expr.call] ,我很难在标准中找到任何明确的语句,即构造函数调用应该以相同的方式工作。 |