为什么C ++委员会决定const引用应该延长临时工作的寿命?
这个事实已经在网上广泛讨论过,包括stackoverflow。解释这种情况的最终资源可能就是GoTW:
GotW #88: A Candidate For the “Most Important const”
此语言功能的基本原理是什么?它知道了吗?
(替代方案是临时的寿命不会被任何参考文献扩展。)
我自己的宠物理论的基本原理是这种行为允许对象隐藏实现细节。使用此规则,成员函数可以在不对客户端代码进行任何更改的情况下,在返回值或const引用与已内部存在的值之间切换。例如,矩阵类可能能够返回行向量和列向量。为了最小化副本,可以返回一个或另一个作为参考,具体取决于实现(行主要与列主要)。无论通过引用返回哪一个都必须通过复制并返回该值来返回(如果返回的向量是连续的)。库编写者可能希望在未来改变实现(行主要与列专业),并防止客户端编写强烈依赖于实现是行主要还是列主要的代码。通过要求客户端接受返回值为const ref,矩阵类可以返回const引用或值,而无需对客户端代码进行任何更改。无论如何,如果原始的理由是已知的,我想知道它。
答案 0 :(得分:16)
它是在1993年提出的。它的目的是在绑定参考时消除对临时工具的不一致处理。
当时,没有像RVO这样的东西,所以简单地禁止临时绑定到引用就会受到性能影响。
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/1993/N0345.pdf
答案 1 :(得分:3)
你不是在质疑为什么允许const引用绑定到临时对象,而只是为什么它们会延长那些临时对象的生命周期。
考虑以下代码:
struct A
{
void foo() const;
};
A bar();
const A& a = bar();
a.foo(); // (1)
如果bar()
返回的临时值的生命周期没有延长,那么a
的任何使用(由第(1)行示例)都会导致未定义的行为。这会使对temporaries的非参数const引用的绑定完全无用。
编辑(寻址OP's comment):
因此,真正的问题应该是为什么允许const引用变量(不是函数参数)绑定到临时变量。我不知道它的原始理由(Richard Hodges' answer可能是唯一真实的理由),但它为我们提供了一个有用的功能。考虑以下示例:
struct B
{
virtual void foo() const;
};
B bar();
const B& b = bar();
b.foo(); // (1)
此示例与上一个示例的唯一区别在于B::foo()
是虚拟的。现在,如果我们决定引入新类D
作为B
的子类并将bar()
的返回类型从B
更改为D
,该怎么办?< / p>
struct B
{
virtual void foo() const;
};
struct D : B
{
virtual void foo() const;
};
//B bar();
D bar();
const B& b = bar();
b.foo(); // This will call D::foo()
// In the end the temporary bound by b will be correctly destroyed
// using the destructor of D.
因此,对temporaries的绑定const引用简化了对由value返回的对象的动态多态性的优势。