简体   繁体   English

clang vs gcc模板子类在父级中使用前向声明的类

[英]clang vs gcc template child class using forward-declared class in parent

I have a template child class (the template typename is not related to parent or child, so not a CRTP inheritance case), and the parent has a forward-declared class in the private access label section. 我有一个模板子类(模板typename与父或子不相关,因此不是CRTP继承的情况),并且父类在私有访问标签部分中有一个前向声明的类。

GCC (tested on 4.9.2 and 7.2) compiles, but clang (tested on 5.0.0) will complain. GCC(在4.9.2和7.2上测试)编译,但clang(在5.0.0上测试)会抱怨。 This is the repro case: 这是repro案件:

class TestClass
{
public:
    // Forward-declare as public to make compile with clang
    // class Thing;
private:
    // GCC compiles fine with forward-declaration as private but clang gives error
    class Thing;
    friend class Thing;
    void NotifyOfThing();
};

class TestClass::Thing
{
public:
    static void NotifyOfThing() {}
};

template <typename Unrelated>
class ThingImpl final : public Unrelated
{
private:
    void handleThing()
    {
        TestClass::Thing::NotifyOfThing();
    }
};

int main() {
    ThingImpl<TestClass> implementation;
}

Clang throws an error: Clang抛出一个错误:

25 : <source>:25:20: error: 'Thing' is a private member of 'TestClass'
        TestClass::Thing::NotifyOfThing();
                   ^
8 : <source>:8:11: note: declared private here
    class Thing;
          ^
1 error generated.
Compiler exited with result code 1

GCC however accepts this. 然而GCC接受了这一点。

Now if I remove the template declaration, and make ThingImpl a non-template class, GCC will also have the same complaint about Thing being private. 现在,如果我删除模板声明,并使ThingImpl成为非模板类​​,GCC也会抱怨Thing是私有的。

Can someone explain why this is the case, and which one complies more with the C++ standard? 有人可以解释为什么会出现这种情况,哪一个更符合C ++标准? Or does the standard not cover this explicitly? 或者标准没有明确涵盖这一点?

gcc has many bugs when it comes to access checking in templates. 当访问模板中的检查时,gcc有很多错误。 See this meta-bug . 看到这个meta-bug The situation you have matches 41437 exactly: 遇到的情况恰好与41437相符:

class A { struct B { B(); }; };
template<typename T> void f() { A::B b; }
void g() { f<int>(); } // gcc says this is okay

clang is correct, the code is clearly ill-formed. 铿锵是正确的,代码显然是不正确的。 Thing is a private class of TestCalss , and ThingImpl is not a friend of TestClass , so ThingImpl trying to access TestClass::Thing should be an access violation. ThingTestCalss的私有类,而ThingImpl不是TestClass的朋友,因此ThingImpl尝试访问TestClass::Thing应该是访问冲突。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 具有预先声明的类的QSharedDataPointer - QSharedDataPointer with forward-declared class 使用前向声明类的嵌套(尚未定义)类型的部分模板特化 - Partial template specialization using nested (undefined yet) type of a forward-declared class 前向声明的集体成员的前向声明 - Forward declaration of a forward-declared class member 前向声明的类枚举问题的变通方法? - Workarounds for the forward-declared class enumeration problem? 在模板基类中的虚函数中使用前向声明的类,其中构造函数只需要前向声明? - Use a forward-declared class in a virtual function in a template baseclass where the constructor only needs the forward declare? boost :: ptr_list中的向前声明的类 - Forward-declared class in boost::ptr_list 将前向声明的 class 的成员函数声明为朋友 - Declare a member-function of a forward-declared class as friend C++:前向声明的 class 的 using 语句生成错误 C2371 - C++: using-statement of forward-declared class generates error C2371 正向声明的类型和“已经声明为类类型的非类类型” - Forward-declared type and “non-class type as already been declared as a class type” 使用具有前向声明类型的模板 - 安全吗? - Using templates with forward-declared types - safe?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM