标签: rvalue-reference

为什么右值对象不会移动到带有右值参数的函数?

我想知道为什么std::move带有右值参数的函数实际上没有移动任何东西,而是通过引用传递?

特别是当我知道它适用于构造函数时。

我正在运行以下代码:

#include <memory>
#include <iostream>

void consume_ptr(std::shared_ptr<int> && ptr) {
    std::cout << "Consumed " << (void*) ptr.get() << std::endl;
}

int main(int argc, char ** argv)
{
    std::shared_ptr<int> ptr = std::make_shared<int>();
    consume_ptr(std::move(ptr));
    if (ptr) {
        std::cout << "ptr should be moved?" << std::endl;
    }
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

输出是:

ptr should be moved?
Run Code Online (Sandbox Code Playgroud)

根据我读到的所有内容,std::shared_ptr应该已移动到函数内部,这意味着对象本身在将其移动到 后将ptr保持不变,但事实并非如此!nullptrconsume_ptr

我用我的一些带有日志记录的自定义类尝试了它,看起来移动构造函数甚至从未被调用。它在每个编译器和优化级别下都可以重现。

有人可以帮我解决这个问题吗?

c++ rvalue-reference

1
推荐指数
1
解决办法
532
查看次数

将对象的所有权传递给同一对象的方法?

我遇到了类似于以下(或多或少最小)示例的 C++ 代码。请考虑底部函数中标记的方法调用:

#include <memory>

static unsigned returnValue = 5;
void setReturnValue(unsigned u) { returnValue = u; }

class MyObject
{
    public:
        MyObject(unsigned uIN) : u(uIN) {}
        ~MyObject() { u = 42; }

        void method(std::unique_ptr<MyObject> uniqPtrToObject)
        {
            // Do something fancy with this unique pointer now, 
            // which will consume the object and its data
            setReturnValue(uniqPtrToObject->getValue());
        }
        unsigned getValue() { return u; }

    private:
        unsigned u;    // Some relevant object data
};

std::unique_ptr<MyObject> GetUniqToObject(unsigned u)
{
    // Get the object …
Run Code Online (Sandbox Code Playgroud)

c++ ownership-semantics rvalue-reference unique-ptr c++14

1
推荐指数
1
解决办法
158
查看次数

C++ 在模板参数和 lambda 的“auto”参数之间转发引用方面的差异

比较以下两种情况:

template<class... Args>
void f1(Args&&... args) { do_smth(std::forward<Args>(args)...); }

auto f2 = [](auto&&... args) { do_smth(std::forward<decltype(args)>(args)...); };
Run Code Online (Sandbox Code Playgroud)

std::forward传递或不传递的类型是否有任何差异?

根据我的理解,当您使用 , 指定转发引用时T&&&&并不与传递的参数“匹配”,而是一种将“原始引用”信息“存储”到T(T将是&, const &,&&const &&根据值类别传递的参数),然后将此类“原始引用”信息结合起来,使用通常的规则等&&计算最终的引用类型。& + && = &

我不知道的是,是否decltype(args)会解析为此类计算“之前”或“之后”的类型,或者结果类型是否与“原始引用”不同,因此指定的类型是否有任何差异std::forwardf1f2.

注意:我不能使用 C++20,并且模板 lambda 不在问题范围内。

c++ reference rvalue-reference forwarding-reference c++17

1
推荐指数
1
解决办法
109
查看次数

rvalue对原始整数的引用何时是短暂的或长寿的?

我用TDM-GCC 4.6.1编译器对rvalue引用做了一些实验,并做了一些我无法用理论解释的有趣观察.我想那里的专家帮我解释一下.

我有一个非常简单的程序,不处理对象,但int原语,并定义了2个函数:foo1(通过rvalue引用返回局部变量)和foo2(按值返回局部变量)

#include <iostream>

using namespace std;

int &&foo1();
int foo2();

int main()
{

int&& variable1 = foo1();
//cout << "My name is softwarelover." << endl;
cout << "variable1 is: " << variable1 << endl; // Prints 5.
cout << "variable1 is: " << variable1 << endl; // Prints 0.

int&& variable2 = foo2();
cout << "variable2 is: " << variable2 << endl; // Prints 5.
cout << "variable2 is still: " << variable2 << endl; // Still prints …
Run Code Online (Sandbox Code Playgroud)

c++ rvalue-reference c++11

0
推荐指数
1
解决办法
415
查看次数

引入rvalue引用实际上有用吗?

将rvalue引用引入C++的典型原因是在评估复杂的C++表达式时消除(优化)多余的复制.

但是,C++ 98/C++ 03 有两种编译器优化技术,它们基本上用于相同的目的,即

有没有任何真实的用例,当上述技术(使用适当编写的代码)无法消除多余的复制,但右值引用可以成功吗?

c++ language-design rvalue-reference c++11

0
推荐指数
2
解决办法
439
查看次数

带有rvalue param调用的C++ 11模板化函数

在某些O类中,我有模板化的函数test2:

struct A{int value;};

struct O{
    A value;

    template<typename Args>
    static void test2(Args &&args){
        std::cout << std::endl << "!!!" << std::is_rvalue_reference<decltype(args)>::value << std::endl;
    }
};
Run Code Online (Sandbox Code Playgroud)

比,我想从另一个调用此函数:

template<typename Args>
void test(Args &&args){
    using t = decltype(std::forward<Args>(args).value);
    std::cout << std::is_rvalue_reference<decltype(args)>::value;
    std::cout << std::is_rvalue_reference<decltype(std::forward<Args>(args).value)>::value;
    std::cout << std::is_rvalue_reference<t>::value;

    // All ok
    O.test2(std::forward<Args>(args).value);            

    // Alvays rvalue, even if agrs is lvalue
    O::template test2<t>(
        std::forward<t>(
            std::forward<Args>(args).value
        )
    );

   // Nor work at all, cant cast A to A&&
   O::template test2<t>(
        std::forward<Args>(args).value
    );
);

} …
Run Code Online (Sandbox Code Playgroud)

c++ templates rvalue-reference c++11

0
推荐指数
1
解决办法
205
查看次数

如何实现可移动的重载而不违反C++中的DRY原则?

虽然在我的一些类中实现方法和运算符重载以利用C++中的右值引用,但我经常编写一些设计不良而违反DRY原则的代码.对于下面的代码片段,什么是更好的替代方案?(这段代码只是为了说明问题)

class matrix_2_2
{
    int _m[2][2];

public:

    matrix_2_2 operator*(const matrix_2_2& m) const &
    {   
        matrix_2_2 res;
        for(int i = 0 ; i < 2 ; i ++)
            for(int j = 0 ; j < 2 ; j++)
                for(int k = 0 ; k < 2 ; k++)
                    res._m[i][j] = (res._m[i][j] + _m[i][k]*m._m[k][j]);

        return res;
    }

    matrix_2_2 operator*(matrix_2_2&& m) &&
    {
        matrix_2_2 res;
        for(int i = 0 ; i < 2 ; i ++)
            for(int j = 0 ; j < …
Run Code Online (Sandbox Code Playgroud)

c++ operator-overloading rvalue-reference c++11

0
推荐指数
1
解决办法
92
查看次数

是否有可能避免重复元组上的std :: move()?

假设我有一个元组和一个函数:

typedef std::tuple< std::unqiue_ptr<int>, std::unqiue_ptr<char> > SomeTuple;          
void someFunction( std::unqiue_ptr<int>, std::unqiue_ptr<char> );
Run Code Online (Sandbox Code Playgroud)

所以在辅助函数中我将元组展开为参数:

void unroll( SomeTuple &t )
{
    someFunction( std::get<0>( std::move( t ) ), std::get<1>( std::move( t ) ) );
}
Run Code Online (Sandbox Code Playgroud)

它有效,但我想避免重复std::move多次.天真的解决方案如:

void unroll( SomeTuple &t )
{
    auto &&rt = std::move( t );
    someFunction( std::get<0>( rt ), std::get<1>( rt ) );
}
Run Code Online (Sandbox Code Playgroud)

显然不起作用,因为rt是一个lvalue.那么有没有办法避免std::move()每次重复多次std::get

c++ rvalue-reference move-semantics c++11 stdtuple

0
推荐指数
1
解决办法
193
查看次数

如何将const std :: shared_ptr插入到std :: map中

请考虑以下代码:

#include <string>
#include <map>
#include <memory>
#include <utility>
#include <iostream>

typedef std::shared_ptr<const std::string> ConstDataTypePtr;
typedef std::map<std::string, ConstDataTypePtr> StrDataTypeMap;

int main()
{
    StrDataTypeMap m_nameToType;
    ConstDataTypePtr vp_int8(new std::string("RGH"));
    m_nameToType.insert(std::make_pair<std::string, ConstDataTypePtr>("int8_t", vp_int8));
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

你必须用:编译它g++ -std=c++11 <filename>.cpp.

它给出以下错误:

    testO.cpp: In function ‘int main()’:
testO.cpp:14:88: error: no matching function for call to ‘make_pair(const char [7], ConstDataTypePtr&)’
     m_nameToType.insert(std::make_pair<std::string, ConstDataTypePtr>("int8_t", vp_int8));
                                                                                        ^
testO.cpp:14:88: note: candidate is:
In file included from /usr/include/c++/4.8.2/bits/stl_algobase.h:64:0,
                 from /usr/include/c++/4.8.2/bits/char_traits.h:39,
                 from /usr/include/c++/4.8.2/string:40,
                 from testO.cpp:1:
/usr/include/c++/4.8.2/bits/stl_pair.h:276:5: note: template<class _T1, class …
Run Code Online (Sandbox Code Playgroud)

c++ rvalue-reference c++11

0
推荐指数
1
解决办法
3938
查看次数

static_cast int要引用int吗?

是否允许:

int x = 1;
int r1 = static_cast<int&>(x);
int r2 = static_cast<int&&>(x)
Run Code Online (Sandbox Code Playgroud)

如果是,那么这些演员表的含义是什么?

这个代码引起了问题:

int x = 1;
int y = 2;
std::swap(x, y); // uses int temp = std::move(x);
Run Code Online (Sandbox Code Playgroud)

c++ static-cast rvalue-reference c++11

0
推荐指数
1
解决办法
85
查看次数