为什么模板参数中的enable_if_t抱怨重新定义? [英] Why does enable_if_t in template arguments complains about redefinitions?
问题描述
我有以下情况可以使用 std :: enable_if
:
I have the following case that works using std::enable_if
:
template<typename T,
typename std::enable_if<std::is_same<int, T>::value>::type* = nullptr>
void f() { }
template<typename T,
typename std::enable_if<std::is_same<double, T>::value>::type* = nullptr>
void f() { }
现在,我在cppreference中看到了新语法在我看来更干净: typename = std :: enable_if_t< std :: is_same< int,T> :: value>>>
Now, I saw in cppreference the new syntax, much cleaner in my opinion : typename = std::enable_if_t<std::is_same<int, T>::value>>
我想移植我的代码:
template<typename T,
typename = std::enable_if_t<std::is_same<int, T>::value>>
void g() { }
template<typename T,
typename = std::enable_if_t<std::is_same<double, T>::value>>
void g() { }
但现在GCC(5.2)抱怨:
But now GCC (5.2) complains :
error: redefinition of 'template<class T, class> void g()'
void g() { }
为什么这样?在这种情况下,如果可以的话,我该怎么做才能拥有新的,更简洁的语法?
Why is that so ? What can I do to have the new, more concise syntax in this case if this is possible ?
推荐答案
让我们删除一些代码。
Let's remove some code.
template<
class T,
class U/* = std::enable_if_t<std::is_same<int, T>::value>*/
>
void g() { }
template<
class T,
class U/* = std::enable_if_t<std::is_same<double, T>::value>*/
>
void g() { }
如果编译器拒绝了以上两个,您会感到惊讶吗
would you be surprised if the compiler rejected the two above templates?
它们都是类型 template< class,class> void()
的模板函数。第二类型参数具有不同的 default 值的事实无关紧要。这就像期望两个具有不同的默认 int
值的 print(string,int)
函数重载一样。 ;)
They are both template functions of "type" template<class,class>void()
. The fact that the 2nd type argument has a different default value matters not. That would be like expecting two different print(string, int)
functions with different default int
values to overload. ;)
在第一种情况下,我们有:
In the first case we have:
template<
typename T,
typename std::enable_if<std::is_same<int, T>::value>::type* = nullptr
>
void f() { }
template<
typename T,
typename std::enable_if<std::is_same<double, T>::value>::type* = nullptr
>
void f() { }
在这里我们不能删除 enable_if
子句。更新为 enable_if_t
:
here we cannot remove the enable_if
clause. Updating to enable_if_t
:
template<
class T,
std::enable_if_t<std::is_same<int, T>::value, int>* = nullptr
>
void f() { }
template<
class T,
std::enable_if_t<std::is_same<double, T>::value, int>* = nullptr
>
void f() { }
我还替换了 typename
和 class
。我怀疑您的困惑是因为 typename
有两种含义-一种是作为 template
自变量的标记,以及
I also replaced a use of typename
with class
. I suspect your confusion was because typename
has two meanings -- one as a marker for a kind of template
argument, and another as a disambiguator for a dependent type.
这里的第二个参数是一个指针,其类型取决于第一个。编译器在没有先替换为 T
类型之前就无法确定这两个是否冲突-您将注意到它们永远不会真正冲突。
Here the 2nd argument is a pointer, whose type is dependent on the first. The compiler cannot determine if these two conflict without first substituting in the type T
-- and you'll note that they will never actually conflict.
这篇关于为什么模板参数中的enable_if_t抱怨重新定义?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!