在 Stroustrup 的 C++ Programming Language book(第 3 版)中,在 Numerics 章节中,他展示了以下代码片段:
void f(valarray<double>& d)
{
slice_array<double>& v_even = d[slice(0,d.size()/2,2)];
slice_array<double>& v_odd = d[slice(1,d.size()/2,2)];
v_odd *= v_even;
v_even = 0;
}
问题是,v_even
并且v_odd
是对临时对象的非常量引用,这是不允许的。并尝试编译它会发出错误:
error: non-const lvalue reference to type 'slice_array<double>' cannot bind to a temporary of type 'slice_array<double>'
slice_array<double>& v_even = d[slice(0,d.size()/2,2)];
^ ~~~~~~~~~~~~~~~~~~~~~~~~
我检查了所有在线可用的勘误表,没有任何内容涉及这个基本问题。我错过了什么吗?自从这本书出版以来,这方面的语言是否发生了变化(不太可能,因为这本书本身提到了反对非常量引用临时变量的规则)?这里发生了什么?
如果我修改函数以使用值而不是引用,例如slice_array<double> v_even = ...
,那么这实际上是编译的。然而,事实证明我的本地 C++ 头文件使复制构造函数公开,而 Stroustrup 和各种在线参考(cppreference.com、cplusplus.com)声称复制构造函数是私有的。我认为这意味着这个解决方案是不可移植的。Stroustrup 明确列出了一个带有非引用变量的代码示例,并表示这会产生错误,这一事实进一步强化了这一点。
C++98 规范 ( PDF ) 声明slice_array<T>
具有私有复制构造函数。到 2005 年(根据这个规范),大概是作为 C++03 的一部分,这变成了一个公共复制构造函数。