从模板化类中的子类访问定义

时间:2017-05-22 17:36:06

标签: c++ templates

我很难构建一个类,它本身包含一个子类,它自己派生自需要来自顶级类的模板参数的类。听起来很可怕,而且在一些MTP建设中确实很深。但是看看我可以从实际代码中缩小的一个简单示例。

我保留原始来源中的姓名。它们在这里并不重要。

template <typename ... T>
class ConstructAll: public T...
{
    public:
        using ConstructorParms = int;
        using BASES_T = ConstructAll<T...>;
        ConstructAll(int){}
};

template <typename T>
class WithTemplate
{
};

class WithoutTemplate
{
};


template <typename X>
class CircuitFromNetlist
{
    private:
        class SerialReader: public ConstructAll<
                            WithTemplate<X>    // use this-> don't compile
                            //WithoutTemplate  // but this works
                            >
    {
        public:
            SerialReader( typename BASES_T::ConstructorParms p): BASES_T( p ) {}
    };

    public:
        CircuitFromNetlist()
        {
            SerialReader ser{1};
        }
};

int main()
{
    CircuitFromNetlist<int> c;
}

如果我使用WithTemplate<X>它没有编译并遇到:

main.cpp:31:40:错误:'BASES_T'尚未声明                  SerialReader(typename BASES_T :: ConstructorParms p):BASES_T(p){}                                         ^ ~~~~~~ main.cpp:在构造函数'CircuitFromNetlist :: SerialReader :: SerialReader(int)'中: main.cpp:31:70:错误:类'CircuitFromNetlist :: SerialReader'没有任何名为'BASES_T'的字段                  SerialReader(typename BASES_T :: ConstructorParms p):BASES_T(p){}

如果我将代码翻转为使用非模板化类,它似乎可以工作。

有什么想法让事情发挥作用?

1 个答案:

答案 0 :(得分:0)

根据C ++ 11标准,您在这里看到的实际上是正确的行为:

  

在类或类模板的定义中,如果基类依赖于模板参数,则在非标准名称查找期间不会检查基类范围,或者在定义类模板或成员或在类模板或成员的实例化期间。 - [temp.dep](强调我的)

ConstructAll<WithoutTemplate>继承时,基类不依赖于模板参数X,但显然从ConstructAll<WithTemplate<X>>继承基类确实依赖于此模板参数。

您必须明确将类型称为typename ConstructAll<WithTemplate<X>>::BASES_T