std::move(const shared_ptr reference) 是什么意思?
what does std::move(const shared_ptr reference) mean?
以下是我正在尝试的玩具代码...我理解第一个和第二个。第一个将所有权授予 _p
。第二个复制 p
到 _p
。
但是我不明白第三个...
const shared_ptr &
的 std::move
是什么意思?谢谢。
class P { };
class A {
public:
// first one
A(std::shared_ptr<P> &p, int) : _p(std::move(p))
{
std::cout << "1st Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
// second one
A(const std::shared_ptr<P> &p, std::string) : _p(p)
{
std::cout << "2nd Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
// third one
A(const std::shared_ptr<P> &p) : _p(std::move(p))
{
std::cout << "3rd Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
private:
std::shared_ptr<P> _p;
};
int main()
{
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p, 1);
std::cout << "1. body: " << p.use_count() << std::endl;
}
std::cout << "-------------" << std::endl;
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p, "2");
std::cout << "2. body: " << p.use_count() << std::endl;
}
std::cout << "-------------" << std::endl;
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p);
std::cout << "3. body: " << p.use_count() << std::endl;
}
}
结果是:
$ ./a.out
1st Ctor: 0, 1
1. body: 0
-------------
2nd Ctor: 2, 2
2. body: 2
-------------
3rd Ctor: 2, 2
3. body: 2
(更新:添加评论以阐明哪个是第一个,第二个等等)
std::move
只是执行转换并产生xvalue(右值)。
当传递 const std::shared_ptr<P>
时,它的 return 类型将是 const std::shared_ptr<P>&&
。然后对于 _p(std::move(p))
将调用右值引用 non-const) 的 copy constructor of std::shared_ptr
(but not move constructor ,效果与第二种情况相同。
移动操作基本上倾向于对被移动的对象进行修改;它不适用于 const
个对象。
std::move
是一个将参数转换为右值引用的函数。函数调用是一个 xvalue 表达式。
当参数是对const 的引用时,转换的结果是const 的右值。如果从右值初始化为 const,将使用复制构造函数,因为移动构造函数的 non-const 的右值引用参数不能绑定到 const.
的右值引用参数
I think there is also an implicit question by OP of how _p(std::move(p))
might differ from _p(p)
_p(std::move(p))
在 const std::shared_ptr<T>
的情况下与 _p(p)
没有区别。
理论上,如果 decltype(_p)
是具有构造函数 T(const T&&)
的类型,那么就会有所不同,因为该构造函数将由 _p(std::move(p))
而不是 _p(p)
。这样的构造函数会很不传统,但在技术上是合式的。 std::shared_ptr
没有这样的构造函数。
以下是我正在尝试的玩具代码...我理解第一个和第二个。第一个将所有权授予 _p
。第二个复制 p
到 _p
。
但是我不明白第三个...
const shared_ptr &
的 std::move
是什么意思?谢谢。
class P { };
class A {
public:
// first one
A(std::shared_ptr<P> &p, int) : _p(std::move(p))
{
std::cout << "1st Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
// second one
A(const std::shared_ptr<P> &p, std::string) : _p(p)
{
std::cout << "2nd Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
// third one
A(const std::shared_ptr<P> &p) : _p(std::move(p))
{
std::cout << "3rd Ctor: "
<< p.use_count() << ", " << _p.use_count() << std::endl;
}
private:
std::shared_ptr<P> _p;
};
int main()
{
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p, 1);
std::cout << "1. body: " << p.use_count() << std::endl;
}
std::cout << "-------------" << std::endl;
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p, "2");
std::cout << "2. body: " << p.use_count() << std::endl;
}
std::cout << "-------------" << std::endl;
{
std::shared_ptr<P> p = std::make_shared<P>();
A a(p);
std::cout << "3. body: " << p.use_count() << std::endl;
}
}
结果是:
$ ./a.out
1st Ctor: 0, 1
1. body: 0
-------------
2nd Ctor: 2, 2
2. body: 2
-------------
3rd Ctor: 2, 2
3. body: 2
(更新:添加评论以阐明哪个是第一个,第二个等等)
std::move
只是执行转换并产生xvalue(右值)。
当传递 const std::shared_ptr<P>
时,它的 return 类型将是 const std::shared_ptr<P>&&
。然后对于 _p(std::move(p))
将调用右值引用 non-const) 的 copy constructor of std::shared_ptr
(but not move constructor ,效果与第二种情况相同。
移动操作基本上倾向于对被移动的对象进行修改;它不适用于 const
个对象。
std::move
是一个将参数转换为右值引用的函数。函数调用是一个 xvalue 表达式。
当参数是对const 的引用时,转换的结果是const 的右值。如果从右值初始化为 const,将使用复制构造函数,因为移动构造函数的 non-const 的右值引用参数不能绑定到 const.
的右值引用参数I think there is also an implicit question by OP of how
_p(std::move(p))
might differ from_p(p)
_p(std::move(p))
在 const std::shared_ptr<T>
的情况下与 _p(p)
没有区别。
理论上,如果 decltype(_p)
是具有构造函数 T(const T&&)
的类型,那么就会有所不同,因为该构造函数将由 _p(std::move(p))
而不是 _p(p)
。这样的构造函数会很不传统,但在技术上是合式的。 std::shared_ptr
没有这样的构造函数。