使用enable_if作为模板参数的模板类方法定义

Sam*_*rsa 10 c++ templates

我之前问了这个问题,提出了一个解决方案.就问题而言,解决方案很棒,但现在我对如何在类外部定义方法感到困惑,即我想在.inl文件中定义方法.在这种情况下,语法是什么?

为了清楚起见,对于模板类,方法定义将是:

template <typename T>
struct Foo
{
  Foo();
};

// C-tor definition
template <typename T>
Foo<T>::Foo()
{
}
Run Code Online (Sandbox Code Playgroud)

如何enable_if使用参数之一定义模板类的方法?

template <typename Policy, enable_if< is_base<BasePolicy, Policy>::value >::type >
struct Foo
{
  Foo();
};

// C-tor definition -- ???
Run Code Online (Sandbox Code Playgroud)

Die*_*ühl 14

从它的外观来看,你想要做的事情就是:

template <typename Policy,
          typename = typename std::enable_if<std::is_base_of<BasePolicy, Policy>::value>::type >
struct Foo;

template <typename Policy>
struct Foo<Policy> {
    Foo();
};

template <typename Policy>
Foo<Policy>::Foo() {
}
Run Code Online (Sandbox Code Playgroud)

这偷偷地利用了几个地方的默认参数:不要混淆,void在几个地方有隐含的坐姿.


Luc*_*ton 8

以下是SFINAE如何实际使用部分专业化:

template<typename T, typename Sfinae = void>
struct Foo {
    /* catch-all primary template */
    /* or e.g. leave undefined if you don't need it */
};

template<typename T>
struct Foo<T, typename std::enable_if<std::is_base_of<BasePolicy, T>::value>::type> {
    /* matches types derived from BasePolicy */
    Foo();
};
Run Code Online (Sandbox Code Playgroud)

然后,可以通过以下方式笨拙地介绍该构造函数的定义:

template<typename T>
Foo<T, typename std::enable_if<std::is_base_of<BasePolicy, T>::value>::type>::Foo()
{
    /* Phew, we're there */
}
Run Code Online (Sandbox Code Playgroud)

如果您的编译器支持模板别名(它是C++ 11特性),那么您可以减少许多冗长:

template<typename T>
using EnableIfPolicy = typename std::enable_if<std::is_base_of<BasePolicy, T>::value>::type;

// Somewhat nicer:

template<typename T>
struct Foo<T, EnableIfPolicy<T>> {
    Foo();
};

template<typename T>
Foo<T, EnableIfPolicy<T>>::Foo() {}
Run Code Online (Sandbox Code Playgroud)

注意:您的原始答案是指Boost的实用程序,例如boost::enable_if_cboost::is_base_of.如果您使用的是不是std::enable_ifstd::is_base_of(这是从C + + 11),然后使用看起来像

typename boost::enable_if<boost::is_case_of<BasePolicy, T> >::type
Run Code Online (Sandbox Code Playgroud)

它具有摆脱一个的优势::value.