我尝试实现
std::move
,它使用 std::remove_reference
,但似乎没有它也能工作。请给我一个例子,如果没有 std::remove_reference
,我的实现将会失败。
template <class type> type && move(type & source) { return (type &&) source; }
template <class type> type && move(type && source) { return (type &&) source; }
std::remove_reference
仅用于避免过载std::move
吗?
这里有一个测试课程可以帮助您:
class test {
public :
test() { }
test(const test & source) { std::cout << "copy.\n"; }
test(test && source) { std::cout << "move.\n"; }
};
不是std::move()如何将值传输到RValues?的重复,因为我的问题包括一个示例,似乎表明
std::remove_reference
在这种情况下+子问题是无用的。
我尝试实现 std::move,它使用 std::remove_reference,但似乎没有它也能工作。
是的,它正在工作,因为您显式地提供了左值引用的重载。而
std::remove_reference
仅在您使用转发引用时才相关。
如果去掉这一行: 神箭
template <class type> type && move(type & source) { return (type &&) source; }
并将您的函数称为:
test t2 = move(t1); //prints copy
要实现此功能,您必须使用
std::remove_reference
。 尝试Godbolt:
template <class type>
std::remove_reference_t<type> && move(type && source)
{
return
static_cast<std::remove_reference_t<type>&& >(source);
}
实现似乎有效,但两个函数声明重叠。
template <class type> type && move(type && source) { return (type &&) source; }
此处
type && source
被解释为通用参考而不是 r 值参考。因此,它可以接受任何输入,包括左值引用,并且对于左值引用输入,它将返回左值引用输出 - 这是一个潜在的问题。
最好避免多个模板函数声明可以接受相同输入的情况,因为这可能会导致各种问题。尽管如此,也许存在一个 C++ 标准规则,在处理通用引用时强制调用某些模板函数声明而不是其他函数声明。您需要向语言律师询问该信息。
您可以使用
std::remove_reference
通过单个模板函数声明来实现移动,如下所示:
template <class type>
std::remove_reference_t<type> && move(type && source)
{
return (std::remove_reference_t<type>&&) source;
}
一般来说,在处理通用引用时,
std::remove_reference
有助于确定哪种类型作为输入给出,并从中获取一些进一步的信息(尽管通常使用std::remove_cv_ref_t
或等效项)。