为什么派生模板类不能访问基模板类的标识符?

时间:2023-02-23
本文介绍了为什么派生模板类不能访问基模板类的标识符?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着跟版网的小编来一起学习吧!

问题描述

考虑:

template <typename T>
class Base
{
    public:
        static const bool ZEROFILL = true;
        static const bool NO_ZEROFILL = false;
}

template <typename T>
class Derived : public Base<T>
{
    public: 
        Derived( bool initZero = NO_ZEROFILL );    // NO_ZEROFILL is not visible
        ~Derived();
}

我无法使用 GCC g++ 3.4.4 (cygwin) 编译它.

I am not able compile this with GCC g++ 3.4.4 (cygwin).

在将这些转换为类模板之前,它们是非泛型的,派生类能够看到基类的静态成员.这是 C++ 规范要求的可见性损失还是我需要使用的语法更改?

Prior to converting these to class templates, they were non-generic and the derived class was able to see the base class's static members. Is this loss of visibility in a requirement of the C++ spec or is there a syntax change that I need to employ?

我知道 Base 的每个实例化都会有它自己的静态成员ZEROFILL"和NO_ZEROFILL",即 Base<float>::ZEROFILLBase<double>::ZEROFILL 是不同的变量,但我并不在乎;常量是为了代码的可读性.我想使用静态常量,因为它在名称冲突方面比宏或全局更安全.

I understand that each instantiation of Base<T> will have it's own static member "ZEROFILL" and "NO_ZEROFILL", that Base<float>::ZEROFILL and Base<double>::ZEROFILL are different variables, but i don't really care; the constant is there for readability of the code. I wanted to use a static constant because that is more safe in terms of name conflicts rather than a macro or global.

推荐答案

这对您来说是两阶段查找.

That's two-phase lookup for you.

Base<T>::NO_ZEROFILL(所有大写标识符都是 boo,除了宏,顺便说一句)是一个依赖于 T 的标识符.
因为,当编译器第一次解析模板时,还没有替换 T 的实际类型,所以编译器不知道"Base 是什么.因此,它无法知道您假设在其中定义的任何标识符(编译器稍后才看到某些 T 的特殊化),并且您不能从定义的标识符中省略基类限定基类.

Base<T>::NO_ZEROFILL (all caps identifiers are boo, except for macros, BTW) is an identifier that depends on T.
Since, when the compiler first parses the template, there's no actual type substituted for T yet, the compiler doesn't "know" what Base<T> is. So it cannot know any identifiers you assume to be defined in it (there might be a specialization for some Ts that the compiler only sees later) and you cannot omit the base class qualification from identifiers defined in the base class.

这就是为什么你必须编写Base::NO_ZEROFILL(或this->NO_ZEROFILL).这告诉编译器 NO_ZEROFILL 是基类中的东西,它依赖于 T,并且它只能在模板被实例化时验证它.因此,它会在不尝试验证代码的情况下接受它.
该代码只能在稍后通过为 T 提供实际参数来实例化模板时进行验证.

That's why you have to write Base<T>::NO_ZEROFILL (or this->NO_ZEROFILL). That tells the compiler that NO_ZEROFILL is something in the base class, which depends on T, and that it can only verify it later, when the template is instantiated. It will therefore accept it without trying to verify the code.
That code can only be verified later, when the template is instantiated by supplying an actual parameter for T.

这篇关于为什么派生模板类不能访问基模板类的标识符?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持跟版网!

上一篇:static_assert 依赖于非类型模板参数(gcc 和 clang 上的不同行为) 下一篇:模板约束 C++

相关文章

最新文章