scoped enum of C++11

Source: Internet
Author: User

The C++11 enumeration type is "Domain" (scoped enum), which has the following advantages over the "non-domain" (unscoped enum) of the C++98 enumeration type:

1 namespace pollution

In general, names that are declared within curly braces are limited by the scope defined by the curly braces, but are exceptions to the non-domain enumeration (unscoped enum)

enum Black  White Red // black, white, red is in same scope as Color  White false // error! White already declared in this scope

    C++11 Domain enumeration (scoped enum), the keyword enum class , can be treated as a "class", thus preventing "namespace contamination" (Namespace pollution)

 enum  class  color {black, white, red} ; //  black, white, red is scoped to color  auto white   = false ; //  fine, no other ' white ' in scope  color c  = white ; //  error! No enumerator named" White "was in this scope  color c  = color::white ; //  fine 

auto C = Color::white ; Also fine

2 Strong Type Enumeration

A non-localized enumeration member that can be implicitly converted to a generalized integer (integral types), as follows:

enum // unscoped enum // func. Returning prime factors of x  = red; if 14.5 // Compare Color to Double (!) {     //  compute Prime factors of a Color (!)     ...}

A domain enumeration member, but cannot be implicitly converted to a generalized integer type

enum class // enum is now scoped  //  as before, but with scope qualifierif14.5)  //  error! Can ' t compare Color and double{    //    ...}

The correct way is to use the C + + type conversion character (CAST)

if (static_cast<Double14.5)     // odd code, but it ' s valid {     //  suspect, but it compiles...    }

3 front-facing statement

A domain enumeration supports a predecessor declaration (forward-declared), which means that an enumeration type can be declared without initializing an enumeration member

enum class Color;

3.1 New Enumeration Members

When a non-unscoped enum (enum) is declared, the compiler chooses a potential type (underlying types) that consumes the least memory to represent each enumeration member

enum Color {black, white, red};  // compiler may choose char type

In the following example, the compiler may choose a larger potential type that can contain a range of 0 to 0xFFFFFFFF

enum Status {     0    , 1,          $ ,     0xFFFFFFFF };

The disadvantage of a non-predecessor declaration is that when a new enumeration member is added (audited in the following example), the entire system will be recompiled, even if only a very simple function uses the new enumeration member (audited)

enum Status {     0,    1,    200,      ,    0xFFFFFFFF};     

With a predecessor declaration, when new enumeration members are added, the header file containing the declarations does not need to be recompiled, and the source file determines whether to recompile based on the usage of the new enumeration member

In the following example, the Status adds an enumeration member audited, and if the function continuteprocesing does not use audited, the implementation of the function continuteprocesing does not need to be recompiled

enum class // Forward Declaration void // Use of fwd-declared enum

3.2 Potential types

The potential type of the domain enumeration (underlying type), the default is int, and of course you can define the potential type yourself. Either way, the compiler will know the size of the enumeration member in advance

enum classStatus;//underlying type is intenum classstatus:std::uint32_t;//underlying type for Status was std::uint32_t (from <cstdint>)enum classstatus:std::uint32_t // specify underlying type on enum ' s definition 
{Good=0, Failed=1, incomplete= -, corrupt= $, audited= -, indeterminate=0xFFFFFFFF};

4 Std::tuple

In general, using the C++11 domain enumeration (scoped enum) is a good choice, but c++98 non-domain enumerations (unscoped enum) are not useless.

4.1 Non-localized enumeration

When it comes to std::tuple, there are advantages to using c++98 non-domain enumerations, as shown in the following example

Suppose a social networking site, each user, uses a template type-tuple (tuple) to contain the name, mailbox, prestige value (name, email, reputation value)

using UserInfo = std::tuple<std::string, std::string//  type alias

When the following code is in a different source file (source files), it is very likely that the first member of the tuple is either a name or a mailbox (name or email)

// object of a tuple type  = std::get<1//  Get value of field 1

However, using a non-domain enumeration (unscoped enum), you can forget about the order of members in the tuple

Enum/  as before= std::get//  Get value of email field 

4.2 Domain Enumeration

In the example above, if you use a domain enumeration (scoped enum), you will use a type conversion, which looks more cumbersome

enum class  // as before= std::get<static_cast<std::size_t> ( Userinfofields::uiemail) >(uinfo);

You can use a template function to associate the enumeration member Userinfofields::uiemail with the std::size_t type.

Template<typename e>constexpr TypeName std::underlying_type<E>:: Type Toutype (E enumerator) noexcept{    return static_cast<typename std::underlying_type<e>::type>( enumerator);}

In this way, the complexity of the code can be reduced slightly. But it still seems a bit cumbersome compared to the non-domain enumeration.

Auto val = std::get<toutype (userinfofields::uiemail) > (uinfo);

Summary:

1) The C++98 enumeration type is "non-domain", while the C++11 enumeration type is "domain" and the enumeration member is visible only within the domain

2) The default potential type (underlying type) for a domain enumeration is type int, and the non-domain enumeration does not have a default potential type

3) A domain enumeration is generally always a predecessor declaration, and a non-domain enumeration can be a predecessor only if a potential type is specified

Resources:

<effective Modern c++> Item 10

scoped enum of C++11

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.