繁体   English   中英

与类型同名的类型别名

[英]Type alias with same name as type

C++ 有效吗?

#include <iostream>


class Test {

    struct Inner {
    };

public:
    using Inner = struct Inner;  // Alias with same name as type
};

int main(int argc, const char * argv[]) {
    static_assert(std::is_pod<Test::Inner>::value, "");
    
    return 0;
}

使用 clang 可以正常编译,但不能使用 GCC / Visual C++(“内部是私有的...”错误消息)

GCC 和 Visual C++ 是正确的。

实际上,您可以使用using来有效地更改成员的访问权限,例如

using Inner_ = Inner;

static_assert(std::is_pod<Test::Inner_>::value, "");

在 function。

但在类型别名与成员同名的情况下,C++ 需要 scope 解析运算符查找成员。 因此,在您的情况下, Test::Inner指的是实际成员而不是using ,因此编译应该失败,因为它是private


请参阅https://en.cppreference.com/w/cpp/language/qualified_lookup ,尤其是

在命名空间 N 的 scope 内进行的限定查找首先考虑位于 N 中的所有声明以及位于 N 的内联命名空间成员(以及可传递地位于其内联命名空间成员中)的所有声明。 如果该集合中没有声明,则它会考虑在 N 中找到的使用指令命名的所有命名空间和 N 的所有传递内联命名空间成员中的声明

P1787R6: Declarations and where to find them ,合并到 C++23 草案中,似乎有利于 Clang 的行为:

[基本.查找]

在某些情况下,仅包含某些类型的声明。 在任何此类限制之后,如果发现任何其他声明,则丢弃任何类或枚举的声明 [注意:类型(但不是typedef 名称或模板)因此被其 scope 中的任何其他实体隐藏。 - 尾注]但是,如果查找是type-only ,则只有类型和模板的声明,其特化是类型被考虑; 此外,如果找到typedef-name和它所引用的类型的声明,则丢弃typedef-name的声明而不是类型声明。

所以struct Inner的声明被丢弃,因为找到了别名声明 (可以将Inner放入仅限类型的上下文中Test::struct Inner根据本段的第二部分,它将引用struct Inner声明)。

暂无
暂无

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM