嗯...我很确定这不是作为未来std::make_unique 的变通实现,但无论如何,该函数的作用很容易理解,尽管它需要您事先了解 C++11 的新特性。
template <typename TT, typename A>
unique_ptr<TT> make_unique(int i, A && a)
{
return unique_ptr<TT>{new TT{ i, std::forward<A>(a) }};
}
首先make_unique是一个函数模板,我真的希望你已经知道了,因为下面会要求你至少有最基本的知识关于模板的作用以及模板的工作原理。
现在到重要的部分。 A && a 有一个函数参数。具体来说,a 是函数参数,其类型为A&&,即r-value reference。由于它的类型是模板类型参数,我们可以从调用者作为参数传递给a 的任何内容推断出它的类型。每当我们有 r 值引用和参数类型推导、特殊推导规则和引用折叠启动时,我们就有一个所谓的“通用引用”,这对于完美的转发功能特别有用。 p>
只要我们有一个通用引用(在我们的例子中是a),我们几乎总是希望在我们想要使用它们时保留其原始的“左值”或“右值”。为了有这种行为,我们几乎应该总是使用std::forward (std::forward<A>(a))。通过使用std::forward,最初作为左值传递的变量仍然是左值,而最初作为右值传递的变量仍然是右值。
之后,事情就简单了
return unique_ptr<TT>{new TT{ i, std::forward<A>(a) }};
注意大括号的使用。它不使用括号,而是使用 C++11 的 uniform initialization 调用构造函数的语法。使用new TT{ i, std::forward<A>(a) },您可以动态分配TT 类型的对象,并在大括号内使用给定的参数。使用unique_ptr<TT>{new TT{ i, std::forward<A>(a) }};,您正在创建一个unique_ptr<TT>,其参数是动态分配返回的参数。然后从函数返回 unique_ptr<TT> 对象。