无法使用模板参数编译类

时间:2018-02-04 17:05:53

标签: c++

我有一些非常简单的代码,看起来像这样:

template <typename T, const T DEFAULT>
class One
{
    T *p;
};

template <typename T, const T DEFAULT>
class Two
{
    One<One<T, DEFAULT>, DEFAULT> *p;
};

当我尝试编译它时,我收到一条错误消息:

  

错误:&#39;第一类&#39;不是模板非类型参数的有效类型

但是,如果我将const T DEFAULT更改为typename T2而将DEFAULT更改为T2,则会开始工作:

template <typename T, typename T2>
class One
{
    T *p;
};

template <typename T, typename T2>
class Two
{
    One<One<T, T2>, T2> *p;
};

但是,这不是我想要的。我需要我的第一个代码工作变体,但我不知道它有什么问题,我该如何解决它。

2 个答案:

答案 0 :(得分:3)

template <typename T, const T DEFAULT>
class One
{
    T *p;
};

template <typename T, const T DEFAULT>
class Two
{
    One<One<T, DEFAULT>, DEFAULT> *p;
};

这有几个问题:

  1. DEFAULTOne<T, DEFAULT>的类型不同; DEFAULT的类型为T。因此,您无法使用One<One<T, DEFAULT>, DEFAULT>

  2. 只有少数类型valid as template non-type parameters。引用cppreference:

      
        
    • std :: nullptr_t(自C ++ 11起);
    •   
    • 整数类型;
    •   
    • 左值引用类型(对象或函数);
    •   
    • 指针类型(对象或函数);
    •   
    • 指向成员类型的指针(指向成员对象或成员函数);
    •   
    • 枚举类型。
    •   
  3. One<T, DEFAULT>不是上述之一,因此不能用作模板非类型参数

答案 1 :(得分:0)

template <typename T, const T DEFAULT>
class One

第二个T引用第一个DEFAULT,它是名为One的非类型模板参数的类型。

例如,您可以像这样实例化One<int, 12345> // T is int, DEFAULT is 123456 模板:

One<char, 100> // T is char, DEFAULT is 100

或者像这样:

One<int*, nullptr> // T is int*, DEFAULT is nullptr

或者像这样:

T

这些示例的共同点是One<std::string, 123> // fails, because `std::string` cannot be used as `DEFAULT` 必须是有效的非类型模板参数。例如,您不能使用类型模板参数:

template <typename T, const T DEFAULT>
class Two
{
    One<One<T, DEFAULT>, DEFAULT> *p;
};

现在,如果你看看你的第二堂课......

One

T的尝试外部实例化中,One<T, DEFAULT>将是std::string。这与上面的One<T, DEFAULT>示例完全相同; Two不是非类型模板参数。

没有&#34;修复&#34;为此,因为你的buildTypes { debug { signingConfig signingConfigs.debug productFlavors { original { buildConfigField "String", "APPINFO", "DEBUG_ORIGINAL" } black { buildConfigField "String", "APPINFO", "DEBUG_BLACK" } } } release { signingConfig signingConfigs.debug productFlavors { original { buildConfigField "String", "APPINFO", "RELEASE_ORIGINAL" } black { buildConfigField "String", "APPINFO", "RELEASE_BLACK" } } } } 课程的概念从根本上被打破了。