为什么在这种情况下调用复制分配?
Why is copy assignment called in this case?
template <typename InfoType>
class ObjPool {
public:
struct tag;
using size_type = unsigned;
using uid_type = IntWrapper<tag, size_type>;
uid_type add(InfoType&& newInfo) {
if (removedUids_.size()) {
uid_type reuse = removedUids_.back();
removedUids_.pop_back();
infos_[reuse] = newInfo; // This line
alive_[reuse] = true;
++size_;
return reuse;
}
else {
infos_.push_back(newInfo);
alive_.push_back(true);
++size_;
return uid_type(size_-1);
}
}
// Other code
};
编译器产生错误:
object of type 'Graph::NodeInfo' cannot be assigned because its copy assignment operator is implicitly deleted
infos_[reuse] = newInfo;
不太明白为什么?我定义了一个 move assignment 并希望这一行调用 move 版本而不是 copy 版本。
为什么是
infos_[reuse] = std::move(newInfo);
这里有必要吗?
用 c++11 的 clang 编译。
右值引用类型的命名变量是左值(感谢@M.M 更正)。它有一个名字,你可以获取它的地址,它与左值引用几乎相同。由于右值引用只能绑定到右值,因此移动赋值运算符不能采用(命名的)右值引用。调用 std::move
将使它成为一个右值(特别是一个 xvalue),以便将其传递给移动运算符。
来自cppreference:
Even if the variable's type is rvalue reference, the expression consisting of its name is an lvalue expression;
template <typename InfoType>
class ObjPool {
public:
struct tag;
using size_type = unsigned;
using uid_type = IntWrapper<tag, size_type>;
uid_type add(InfoType&& newInfo) {
if (removedUids_.size()) {
uid_type reuse = removedUids_.back();
removedUids_.pop_back();
infos_[reuse] = newInfo; // This line
alive_[reuse] = true;
++size_;
return reuse;
}
else {
infos_.push_back(newInfo);
alive_.push_back(true);
++size_;
return uid_type(size_-1);
}
}
// Other code
};
编译器产生错误:
object of type 'Graph::NodeInfo' cannot be assigned because its copy assignment operator is implicitly deleted infos_[reuse] = newInfo;
不太明白为什么?我定义了一个 move assignment 并希望这一行调用 move 版本而不是 copy 版本。
为什么是
infos_[reuse] = std::move(newInfo);
这里有必要吗?
用 c++11 的 clang 编译。
右值引用类型的命名变量是左值(感谢@M.M 更正)。它有一个名字,你可以获取它的地址,它与左值引用几乎相同。由于右值引用只能绑定到右值,因此移动赋值运算符不能采用(命名的)右值引用。调用 std::move
将使它成为一个右值(特别是一个 xvalue),以便将其传递给移动运算符。
来自cppreference:
Even if the variable's type is rvalue reference, the expression consisting of its name is an lvalue expression;