我正在学习 C++ 模板。有人可以解释这段代码的每一点吗
template <class T>
struct identity
{
typedef T type;
};
template <class T>
T&& forward(typename identity<T>::type&& a)
{
return a;
}
我正在学习 C++ 模板。有人可以解释这段代码的每一点吗
template <class T>
struct identity
{
typedef T type;
};
template <class T>
T&& forward(typename identity<T>::type&& a)
{
return a;
}
首先,您需要另一个专业化my_forward
来允许此调用:
int a;
my_forward<int>(a);
因此,专门my_forward
针对这样的参考资料:
template <class T>
T&& my_forward(typename identity<T>::type& a)
{
return static_cast<T&&>(a);
}
但在这种情况下,呼吁
int a;
my_forward<int&>(std::ref(a));
模棱两可:
note: candidate function [with T = int &]
T&& my_forward(typename identity<T>::type&& a)
^
note: candidate function [with T = int &]
T&& my_forward(typename identity<T>::type& a)
^
为避免这种情况,您应该使用std::remove_reference
而不仅仅是identity
:
template <class T>
T&& my_forward(typename std::remove_reference<T>::type&& a)
{
return static_cast<T&&>(a);
}
template <class T>
T&& my_forward(typename std::remove_reference<T>::type& a)
{
return static_cast<T&&>(a);
}
template <class T>
struct identity
{
typedef T type;
};
这部分定义了一个名为的类模板identity
,它包含一个typedef
名为type
您作为模板参数传递的类型的公共成员。在您的示例中,没有部分或显式特化,因此传递给的任何类型identity
都是type
.
template <class T>
T&& forward(typename identity<T>::type&& a)
{
return a;
}
forward
是一个函数模板,对 . 返回的类型进行右值引用identity<T>::type
。type
编译器无法将返回的类型(无论它可能多么明显)推断为T
(因为该类型是依赖类型),因此您必须显式指定forward
.
右值引用语法&&
(用于返回类型)还表示(非正式地)称为通用引用,因为类型T
是模板参数。这意味着返回类型可以绑定到函数返回的右值和左值。
参数类型identity<T>::type&&
不是通用引用,因为返回的类型不是模板参数。这意味着参数只能接受右值。这将要求我们将move
参数左值转换为forward
:
int main()
{
int n{0};
forward<int>(std::move(n));
}
最后我们将参数返回a
给右值引用。但是请注意,返回参数T&&
将不起作用,因为a
必须移动:
template <class T>
T&& forward(typename identity<T>::type&& a)
{
return std::move(a);
}
否则返回一个左值引用:
template <class T>
T& forward(typename identity<T>::type&& a)
{
return a;
}