TheRiver | blog

You have reached the world's edge, none but devils play past here

0%

enum class

参考

effective modern c++

正文

区别1 限定作用域

c++98风格的enum类型的作用域:

1
2
3
4
5
6
7
8
9
10
11
12
enum data {
one,
two,
three,
max
};

int one; //错误 C2365 “one”: 重定义;以前的定义是“枚举数”

int main() {

}

枚举{}内的名字的作用域是在{}外面的范围内的。也叫做不限定作用域的枚举值。

c++11风格的enum类型的作用域:

1
2
3
4
5
6
7
8
9
10
11
12
enum class data {
one,
two,
three,
max
};

int one;

int main() {
::data a = data::one;
}

枚举{}内的名字的作用域是在{}内部的范围内的,也叫做限定作用域的枚举值。

区别2 提前声明

c++98风格的枚举没有默认的型别,会根据实际表示范围决定采用合适的容得下的类型:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
using namespace std;

int main() {

enum data {
one = 0,
};

enum data2 {
one2,
two2,
three2,
max2 = 0XFFFFFFFF
};

cout << sizeof(data) << endl; //4
cout << sizeof(data2) << endl; //4
}

这个没有复现出来,不知道是不是因为字节对齐导致的还是什么原因,98,03,11编译后的结果都是4.按照书里的意思,98版本的枚举要根据实际范围决定采用什么类型,所以不能提前声明,具体如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
#include <iostream>
using namespace std;

enum data; //gcc:错误:使用枚举‘data’前没有给出声明

enum data {
one = 0,
};

int main() {

}

c++11可以显示指定类型,并且enum class有默认的类型int

1
2
3
4
5
6
7
8
9
10
11
12
#include <iostream>
using namespace std;

enum data:uint8_t; //声明必须显示指定类型

enum data:uint8_t {
one = 0,
};

int main() {
cout << sizeof(::data) << endl; //1
}
1
2
3
4
5
6
7
8
9
10
11
using namespace std;

enum class data; //声明可以不指定类型,默认int

enum class data{
one = 0,
};

int main() {
cout << sizeof(::data) << endl; //4
}

区别3 隐式类型转换

98风格的枚举会有隐式类型转换,c++11版本的不会隐式类型转换

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
using namespace std;

enum data98{
one = 0,
};

enum class data11 {
max = 0,
};

void func(size_t param)
{
;
}

int main() {
data98 d98;
data11 d11;
func(d98); //ok
func(d11); //error
//错误(活动) E0167 "data11" 类型的实参与 "size_t" 类型的形参不兼容
}

ending

2020071202.jpg

----------- ending -----------