C++枚举体类型小结
总结一下最近碰到到枚举体相关的知识点:
首先说明一下定义,枚举体是一种数据类型,用于存储用户定义的数据集合,一个枚举体类型定义后, 它和整型数据类型如 int, long 等的用法类似.
定义枚举体时要注意每个枚举体成员的值必须是整型.否则有如下错误:
enum en {a=3.7};
//expression is not an integral constant expression
枚举体类型的占用字节大小为一个int型的大小, 即4个字节.
enum flag {x=1, y=2, z=4, e=8};//sizeof(flag) = 4;
枚举体值的类型即是枚举体.
enum flag {x=1, y=2, z=4, e=8};
flag f = flag::x;
cout << typeid(f).name() << '\n';
输出: 4flag
枚举体变量可以转换为整型,但是整型数不能直接转换成枚举体类型.
enum flag {x=1, y=2, z=4, e=8};
int aa = flag::x; //ok
flag f1 = 5; //cannot initialize a variable of type 'flag' with an rvalue of type 'int'
但是可以用类似用类的构造函数的方法初始化:
flag f2 = flag(4);
PS: 这里要注意的是枚举体的表示范围,像本例中 flag 的表示范围是[0, 15], 如果你用这个范围之外的数据来初始化枚举体变量的话, 例如flag f3 = flag(35)
, 编译器可能不会报错,但是结果却会是 undefined.所以最好不要用整型数初始化枚举体变量.
接着上一个问题, 介绍一下枚举体表示范围的求法:
首先求上限, 你需要找到一个最小正整数k, 使得
2k−1
不小于枚举体成员的最大值.比如上面的定义的enum flag {x=1, y=2, z=4, e=8};
中,枚举体成员最大值为8,满足上述条件的最小的正整数 k是5,所以上限为15.
关于下限,需要分两种情况讨论:
- 枚举体的值均为非负数,则下限为0, 比如上个例子中的flag
下限为0.
- 一般情况与上限求法类似, 你需要找到一个最小正整数k,使得
−2k
不大于枚举体成员中的最小值.
这里举一个例子,加深大家的理解:
定义枚举体: enum e3 {min=-10, max=1000};
这里首先给出它的表示范围为
[−1024,1023]
. 这里上限好理解,不小于1000的最小的2的整数次幂是1024,所以上限应该是
1024−1
也就是1023,但是下限按照下限求法应该是-16, 这里为什么是-1024呢?关于这个问题, Stroustrup给出的解释是表示范围的求法要考虑到smallest bitfield翻译过来可以叫最小域原则,那这个例子来讲,就是说要表示整个枚举体的范围,最小需要10+sign bit 也即是11位,而11位有符号整数的表示范围正是
[−1024,1023]
.
验证代码:
#include <iostream>
#include <numeric>
using std::cout;
enum flag {x=1, y=2, z=4, e=8}; //range 0:15
enum e1 {dark, light}; //range 0:1
int main()
{
cout << sizeof(e1) << '\t' << sizeof(flag) << '\n';
cout << typeid(e1).name() << '\n';
int aa = flag::x;
cout << aa << '\n';
//cannot initialize a variable of type 'flag' with an rvalue of type 'int'
//flag f1 = 5;
flag f2 = flag(5);
cout << typeid(f2).name() << '\n';
cout << f2 << '\n';
flag f3 = flag(z|e);
cout << f3 << '\n';
flag f4 = flag(99); // undefined
cout << f4 << '\n';
// the following code doesn't work as I wish
cout << std::numeric_limits<enum flag>::max() << '\n';
cout << std::numeric_limits<enum flag>::min() << '\n';
return 0;
}
The C++ Programming Language Third Edition Bjarne Stroustrup
http://stackoverflow.com/questions/24826853/c-enumeration-range-bjarne-stroustrup-book