用户定义类型的非类型模板参数

Lem*_*ing 3 c++ templates constexpr c++11

我正在尝试定义一个模板类,它具有用户定义类型的非类型模板参数.不幸的是,迄今没有成功.真正的代码有点过于冗长,但简化示例如下所示:

#include <iostream>

template <class T>
class Maybe {
    bool is_ = false;
    T value_;

  public:
    constexpr Maybe() = default;
    constexpr Maybe(T value) : is_(true), value_(value) {}

    constexpr bool is() const { return is_; }
};

template <Maybe<int> parm>
struct Test {
    void say() const {
        std::cout << "parm is " << (parm.is() ? "set" : "not set") << ".\n";
    }
};

int main() {
    Test<Maybe<int>{}> not_set;
    Test<Maybe<int>(2)> is_set;

    not_set.say();
    is_set.say();
}
Run Code Online (Sandbox Code Playgroud)

当我尝试编译此代码(使用Clang 3.4)时,我收到以下错误消息:

test.cc:15:22: error: a non-type template parameter cannot have type
      'Maybe<int>'
template <Maybe<int> parm>
                     ^
test.cc:23:10: error: value of type 'Maybe<int>' is not implicitly
      convertible to 'int'
    Test<Maybe<int>{}> not_set;
         ^~~~~~~~~~~~
test.cc:24:10: error: value of type 'Maybe<int>' is not implicitly
      convertible to 'int'
    Test<Maybe<int>(2)> is_set;
         ^~~~~~~~~~~~~
3 errors generated.
Run Code Online (Sandbox Code Playgroud)

现在,我知道非类型模板参数必须满足某些条件.但是,我认为constexpr就足够了.或者它真的只能是内置的整体类型之一吗?

有没有办法传递我自己的用户定义类型的非类型模板参数?

For*_*veR 6

不,你不能.

n3376 14.1/7

非类型模板参数不应声明为具有浮点,类或void类型.

template<double d> class X; // error
template<double* pd> class Y; // OK
template<double& rd> class Z; // OK
Run Code Online (Sandbox Code Playgroud)

所以,你可以传递指针或引用,但不能传递类类型的对象.

实例