是否可以为枚举类枚举器添加别名?

Kal*_*ish 23 c++ enums alias language-lawyer c++11

给定一个C++ 11枚举类,嵌套在几个长而丑陋的命名空间中:

namespace
    long_and_ugly
{
    enum class
        colour
    {
        red,
        green,
        blue
    };
}
Run Code Online (Sandbox Code Playgroud)

别名是否可以由枚举值组成?使用clang ++ 3.5,可以执行以下操作:

using long_and_ugly::colour; // take all the values into the current namespace
using long_and_ugly::colour::red; // take only 'red' into the current namespace

function_taking_colour_argument( red ); // instead of fully referring to the value
Run Code Online (Sandbox Code Playgroud)

然而,g ++ 4.9抱怨道.我无法复制其错误消息,因为我无法访问代码,但它明确抱怨使用using指令或声明.我也试过这个:

using red = long_and_ugly::colour::red;
Run Code Online (Sandbox Code Playgroud)

但它也失败了.对不要粘贴错误我很抱歉.不过,我相信你应该能够重现它.


问题(S)

  • 是否可以在标准C++ 11中为枚举值声明别名,或者我是否使用了clang扩展?

  • 如果是,那么正确的语法是什么?

Fil*_*efp 26

使用声明中的枚举

问题是标准表示在使用指定using声明时不应引用枚举类中枚举器.

7.3.3p7 using声明 [namespace.udecl](n3337)

一个using声明不得命名范围的枚举.

namespace N {
  enum class E { A };
}

using N::E;    // legal
using N::E::A; // ill-formed, violation of [namespace.udecl]p7
Run Code Online (Sandbox Code Playgroud)

注意:clang确实接受上面两行; 这是一个相关的错误报告.

引用枚举类本身的实际名称是完全正确的,但尝试引用其枚举器之一是不正确的.


别名声明中的枚举器

标准说,别名声明只能用于引用类型名称,因为枚举器不是一个类型,在这样的上下文中使用一个是不正确的.

namespace N {
  enum class E { A };
}

using x = N::E;     // legal, `N::E` is a type
using y = N::E::A;  // ill-formed, `N::E::A` isn't a type
Run Code Online (Sandbox Code Playgroud)

使用别名声明的替代方法

您可以使用您想要"别名"的值初始化您所选择的任何名称来声明一个常量:

namespace N {
  enum class E { A };
}

constexpr N::E x = N::E::A;
Run Code Online (Sandbox Code Playgroud)
int main () {
  N::E value = x; // semantically equivalent of `value = N::E::A`
}
Run Code Online (Sandbox Code Playgroud)


MSa*_*ers 5

有点:

namespace long_and_ugly {
    enum class colour
    {
        red,
        green,
        blue
    };
}
const colour red = long_and_ugly::colour::red;
Run Code Online (Sandbox Code Playgroud)