C++ Primer第五版笔记--枚举类型

本文深入探讨C++中的枚举类型,包括限定作用域和不限定作用域的枚举,枚举成员的作用域规则,枚举成员的默认值及自定义值,以及如何在代码中使用枚举类型。同时,文章还讲解了如何定义枚举类型的大小,枚举类型的前置声明,以及枚举类型在函数参数匹配中的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

枚举类型可以将一组整型常量组织在一起;和类一样,每个枚举类型定义了一种新的类型;枚举属于字面常量类型
  C++包含两种枚举:限定作用域(C++11新标准引入)的和不限定作用域的:
  定义限定作用域的枚举类型的一般形式是:首先是关键字enum class(或者等价的使用struct),之后是枚举类型名字以及用花括号括起来的以逗号分割开来的枚举成员列表,最后是一个分号
   enum class open_modes{input,output,append};
  定义不限定作用域的枚举类型时省略关键字class(或struct),枚举类型的名字是可选的:
   enum color{red,yelow,blue};
   enum {floatPrec = 6,doublePrec = 10,double_doublePrec = 10};

枚举成员

在限定作用域的枚举类型中,枚举成员的名字遵循常规的作用域准则,并且在枚举类型的作用域外是不可访问的。与之相反,在不限定作用域的枚举类型中,枚举成员的作用域与枚举类型本身的作用域相同:

//定义
enum color{red,yellow,green};			//不限定作用域的枚举
enum stoplight{red,yellow,green};		//报错:重复定义枚举成员
enum class Peppers{red,yellow,green};	//正确,外面的被隐藏了
//使用
coler a = green;						//正确
Peppers p = green;						//报错,这个green被认为是color的
Peppers p2 = Peppers::red;				//正确

默认情况下,枚举成员的值是从0开始的,依次加1,不过是可以专门指定枚举成员的值,并且枚举成员的值也可以不唯一

enum class intTypes{
	charType = 8,shortType = 16,intType = 16,
	longType = 32,long_longType = 64
};

枚举成员是const的,因此在初始化枚举成员时提供的枚举值必须是常量表达式,即每个枚举成员本身就是一条常量表达式,可以在任何需要常量表达式的地方使用枚举成员。例如,定义枚举类型的constexpr(有编译器检查变量是否是一个常量表达式)变量:
  constexpr intTypes ch = intTypes::charType;

枚举定义新的类型

和类一样,枚举也能定义新的类型,只要enum有名字,我们就能定义并初始化enum对象并为该对象赋值,必须使用该类型的一个枚举成员或该类型的另一个对象
  open_modes om = 2;    //错误,2不是该枚举的成员
  om = open_modes::input;   //正确

值得注意的是一个不限定作用域的枚举类型的对象或是枚举成员可以自动转换成整型,可在需要的地方使用:
  int i = color::red;    //正确
  int j = Peppers::red;   //错误,限定作用域的枚举类型不会进行隐式转换。

指定enum大小

尽管每个enum都定义了唯一的类型,但实际上enum是由某种整数类型表示的。在C++11新标准中,可以在enum的名字后面加上冒号以及想在该enum中使用的类型:

enum intValues : unsigned long long {
	charTyp = 255,shortTyp = 65535,intTyp = 65536,
	longTyp = 4294967296UL,
	long_longTyp = 18446744073709551615ULL
};

如果没有指定类型,那么限定作用域的枚举的枚举成员类型默认会是int
对于不限定作用域的枚举来说,不存在默认的类型,只知道成员的潜在类型足够大,肯定能容纳枚举值。

枚举类型的前置声明

在C++11新标准中,可以提前声明enum,该前置声明必须指定其成员的大小:

enum intValues : unsigned long long       //不限定作用域的枚举必须指定成员类型
enum class open_modes;	//限定作用域的枚举类型因为有默认的成员类型,所以不用特意指定

和其他声明一样,enum的声明和定义必须匹配,且不能在同一个文件中先声明一个不限定作用域的enum名字,然后再声明一个同名的限定作用域的enum。

形参匹配与枚举类型

初始化一个enum对象时,必须使用另个enum对象或是该枚举类型的一个枚举成员,因此,即使某个整型值与枚举成员的值相等,它也不能作为函数的enum实参使用:

//不限定作用域的枚举类型
enum Token{
	INLINE = 128,VIRTUAL = 129
};
void f(Token);
void f(int);

int main(){
	Token curTok = INLINE;
	f(128);								//精确匹配的f(int)
	f(INLINE);							//精确匹配的f(Token)
}

虽然不能将整型值传给枚举形参,但是可以将一个不限定作用域的枚举类型的的对象或枚举成员传给整型形参。此时,enum的值转换为int或更大的整型,实际转换的结果由枚举类型的潜在类型(由机器决定)决定:

void newf(unsigned char);
void newf(int);
unsigned char uc = VIRTUAL;
newf(VIRTUAL);							//匹配newf(int)
new(uc);								//匹配newf(unsigned char)
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值