g ++模板bug还是VC过于宽松?

时间:2011-03-16 23:07:05

标签: c++ templates g++

我正在用C ++编写一段模板化的代码。它在VS 2005中运行得很好,但是当我尝试用g ++编译时,我得到了一些非常奇怪的错误。

必不可少的代码(简化为最小,不编译)如下:

template <class Actual>
class Generic
{
public:
    typedef Actual ThisType;
};

template <class Actual>
class Intermediate : public Generic<Actual>
{
};

template <class Q>
class Derived : public Intermediate<Derived<Q> >
{
public:
    void FooBar()
    {
        ThisType q;
    }
};

错误是:     “'ThisType'未在此范围内声明” 在'q'被宣布的行中。

奇怪的是,当Derived不是模板而是普通类时,一切正常。为什么编译器在实例化之前会查看模板函数实现?我知道VC ++在编译模板时检查得太少(未使用的模板甚至可能包含语法上不正确的代码) - 但这里不是g ++检查太多了吗?我尝试添加一个没有希望的typename关键字,它也失败了。有没有办法让ThisType按预期工作?我害怕将它手动添加到每个派生类中的想法 - 它是繁琐,冗余,不优雅和错误诱导。

祝你好运, MZ

4 个答案:

答案 0 :(得分:4)

在依赖的基类中不会查找非限定名称(您的基类依赖于模板参数Q)。限定该名称,它将起作用。

typename Derived::ThisType q;

答案 1 :(得分:1)

信任Comeau online compiler

Comeau C/C++ 4.3.10.1 (Oct  6 2008 11:28:09) for ONLINE_EVALUATION_BETA2
Copyright 1988-2008 Comeau Computing.  All rights reserved.
MODE:strict errors C++ C++0x_extensions

"ComeauTest.c", line 19: error: identifier "ThisType" is undefined
          ThisType q;
          ^

"ComeauTest.c", line 19: error: expected a ";" (perhaps on the previous statement)
          ThisType q;
                   ^

2 errors detected in the compilation of "ComeauTest.c".

不考虑继承类中的依赖类型名称,您可能会尝试显式请求ThisType:

typename Intermediate<Derived<Q> >::ThisType q;

答案 2 :(得分:0)

您缺少 typename

template <class Actual> class Generic { public:
    typedef Actual ThisType; };

template <class Actual> class Intermediate : public Generic<Actual> { };

template <class Q> class Derived : public Intermediate<Derived<Q> > { public:
    void FooBar()
    {
        typename Derived::ThisType q;
        return *this;
    } };

int main(){}

答案 3 :(得分:0)

代码确实是不正确的。当基类依赖于模板参数时,在查找非限定名称时不会通过名称查找来考虑它。

在您的情况下,不会在基类ThisType中查找未限定名称Intermediate<Derived<Q> >,因为您的基类取决于模板参数Q