c – 错误转发右值参考

前端之家收集整理的这篇文章主要介绍了c – 错误转发右值参考前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我正在尝试新增的右值参考(在vs2012 express中).

我不明白.给出下面的代码(大部分来自c标准,其中解释了std :: forward).

struct A
{
    A(int& i,const float& j):
        m_i(i),m_j(j){}

    int& m_i;
    const float& m_j;
};

template<class T,class A1,class A2>
T* factory(A1&& a1,A2&& a2)
{
    return new T(a1,a2);
}

void test()
{

    A* a1 = factory<A>(1,1.2f);

    //How does this work ?        
    a1->m_i = 2;
}

我不明白m_i绑定到哪里.

我将基本上有一个左值引用到右值引用(&&&&),ref refpsing规则变成(&)一个简单的左值引用.但是参考什么?

解决方法

I don’t understand where is m_i binded to.

m_i绑定到A的构造函数的参数. A的构造函数在这里的论点是什么?

在这种情况下,由于工厂不将其参数转发给A(即它不使用std :: forward<>()),那么传递给A的是左值.这是因为命名了a1,命名对象是左值.

a1的类型与确定a1是左值还是右值无关.因此,即使a1具有类型rvalue-reference to int(int&&),就像程序中的情况一样,参数a1本身也是一个命名对象,因此它是一个左值.

这意味着,由于m_i具有对int的类型lvalue-reference,因此m_i可以绑定(并且实际上是绑定)到factory(lvalue)参数a1,该参数将在factory()返回时被销毁.换句话说,你留下了一个悬垂的参考.

试图取消引用它(正如你在程序中稍后所做的那样)会召唤未定义的行为.

但是,如果您的factory()函数已将其参数转发给A的构造函数

template<class T,A2&& a2)
{
    return new T(std::forward<A1>(a1),std::forward<A2>(a2));
}

这会导致编译器错误,因为std :: forward<>()的机制会确保左值保持左值,并且rvalues保持rvalues.尝试将左值引用绑定到右值是非法的,因此对A的构造函数调用将失败.

猜你在找的C&C++相关文章