通常,rvalues可以绑定到const引用(const SomeType&).它是内在的语言.然而,std :: reference_wrapper< const T>不接受作为其构造函数参数的rvalue,因为相应的重载被故意删除.这种不一致的原因是什么?当我们必须通过值但是要保留引用语义的情况下,std :: reference_wrapper是“通告”作为引用变量的替代方法.
换句话说,如果对于const&绑定被认为是安全的,因为它被内置到语言中,为什么C11的设计者不允许rvalue被包装在std :: reference_wrapper< const T>?
什么时候能方便,你可以问.例如:
class MyType{}; class Foo { public: Foo(const MyType& param){} }; class MultiFoo { public: MultiFoo(std::initializer_list<std::reference_wrapper<const MyType>> params){} }; int main() { Foo foo{MyType{}}; //ok MultiFoo multiFoo{MyType{},MyType{}}; //error }
解决方法
将临时直接绑定到参考延长其使用寿命.
struct Foo {}; Foo f() { return {}; } void g() { f(); // temporary destroyed at end of full-expression const Foo& r = f(); // temporary destroyed at end of scope // r can still be used here ... // ... // all the way down to here }
但是,它必须直接绑定到临时.请考虑以下示例:
struct Bar { Bar(const Foo& f): r(f) {} const Foo& r; }; void h() { Bar b(f()); // binding occurs through parameter "f" rather than directly to temporary "f()" // b.r is now a dangling reference! lifetime not extended }
即使你可以,这将使临时的包装变得无用.
注意:实际的引用包装器对象使用指针,以便可以重新分配:
struct Baz { Baz(const Foo& f): p(std::addressof(f)) {} Baz& operator=(const Foo& f) { p = std::addressof(f); return *this; } const Foo* p; };