当前位置: C语言 -- 基础 -- 词法元素

词法元素(四)

四、常量

C语言中常量(constant)包括整数常量(integer-constant)、浮点常量(floating-constant)、枚举常量(enumeration-constatn)、字符常量(character-constant)和预定义常量(predefined-constant)。每个常量都有一个类型,常量值应在其类型可表示的值域范围内,常量的类型由其形式和值共同决定。

:预定义常量是ISO/IEC 9899:2024标准新增的常量。)


1、整数常量

整数常量以数字开头,可能存在指定基数的前缀、指定类型的后缀以及数字分隔符(digit separator);但不存在小数点,也不存在指数部分。

十进制整数常量以非0数字开头,由一个十进制数字序列构成,例如:123。二进制整数常量由前缀0b或者0B,后跟二进制数字构成的序列组成,例如:0B110。八进制整数常量由前缀0,后跟由八进制数字构成的序列(可选)组成,例如:06。十六进制整数常量由前缀0x或者0X,后跟十六进制数字构成的序列组成,字符af(或者AF)分别表示数值1015,例如:0x2c


十进制数字包括:0 1 2 3 4 5 6 7 8 9

二进制数字包括:0 1

八进制数字包括:0 1 2 3 4 5 6 7

十六进制数字包括:0 1 2 3 4 5 6 7 8 9 

a b c d e f

A B C D E F


十进制整数常量值以10为基数计算;二进制整数常量值以2为基数计算;八进制整数常量值以8为基数计算;十六进制整数常量值以16为基数计算。以十进制整数常量24为例,其二进制、八进制、十六进制形式分别为0b110000300x18


数字分隔符是ISO/IEC 9899:2024标准新增内容,用于在整数常量或者浮点常量中分隔数字,符号是单引号字符(')。数字分隔符在整数常量中的语法格式如下所示:

decimal-constant 'opt digit 				//十进制。
binary-constant 'opt binary-digit 			//二进制。
octal-constant 'opt octal-digit 			//八进制。
hexadecimal-digit-sequence 'opt hexadecimal-digit 	//十六进制。							

其中decimal-constant是十进制整数常量,opt表示可选,digit表示十进制数字;binary-constant是二进制整数常量,binary-digit是二进制数字;octal-constant是八进制整数常量,octal-digit是八进制数字;hexadecimal-digit-sequence是十六进制数字序列,hexadecimal-digit是十六进制数字。


确定常量值时数字分隔符会被忽略。

0B1100'1010	//0B1100'1010等价于0B11001010。
1'23'456'7890	//1'23'456'7890等价于1234567890。					

数字分隔符仅用于分隔数字。

0X'FEDC		//数字分隔符的使用非法。
'3'5		//'不是数字分隔符,'3'是字符常量,5是整数常量。						

整数常量类型是下表对应表格中第一个可以表示其值的类型。

整数常量类型
后缀 十进制整数常量 二进制、八进制、十六进制整数常量
无后缀 int
long int
long long int
int
unsigned int
long int
unsigned long int
long long int
unsigned long long int
u或者U unsigned int
unsigned long int
unsigned long long int
unsigned int
unsigned long int
unsigned long long int
l或者L long int
long long int
long int
unsigned long int
long long int
unsigned long long int
ul或者UL unsigned long int
unsigned long long int
unsigned long int
unsigned long long int
ll或者LL long long int long long int
unsigned long long int
ull或者ULL unsigned long long int unsigned long long int
wb或者WB _BitInt(N) _BitInt(N)
uwb或者UWB unsigned _BitInt(N) unsigned _BitInt(N)

在能够容纳值位和符号位的情况下,N为大于1的最小整数值。

在能够容纳值位的情况下,N为大于0的最小整数值。


#define TYPE(x) _Generic((x),				\
              int: "int type",				\
              unsigned int: "unsigned int type",	\
              long int: "long int type",		\
              default: "unknown type"			\
              )

printf("%s\n", TYPE(2147483648));   //输出long int type。
printf("%s\n", TYPE(0x80000000));   //输出unsigned int type。

编译环境中int类型占4个字节,unsigned int类型占4个字节,long int类型占8个字节;宏INT_MAXUINT_MAXLONG_MAX值分别为214748364742949672959223372036854775807。整数常量21474836480x80000000值相同;但进制不同,一个是十进制,一个是十六进制。

整数常量2147483648int → long int → long long int顺序确定类型,因为INT_MAX < 2147483648 < LONG_MAX,所以整数常量2147483648的类型为long int类型。

整数常量0x80000000int → unsigned int → long int → unsigned long int → long long int → unsigned long long int顺序确定类型,因为INT_MAX < 0x80000000 < UINT_MAX,所以整数常量0x80000000的类型为unsigned int类型。


如果一个整数常量(该整数常量不存在wbWBuwb或者UWB后缀。)不能使用其列表中的任何类型表示,但可以使用扩展整数类型表示,则该整数常量具有扩展整数类型。如果整数常量列表中的所有类型都是有符号整数类型,则扩展整数类型应为有符号整数类型。如果整数常量列表中的所有类型都是无符号整数类型,则扩展整数类型应为无符号整数类型。如果列表中同时包含有符号整数类型和无符号整数类型,则扩展整数类型可以是有符号整数类型,也可以是无符号整数类型。如果一个整数常量不能使用其列表中的任何整数类型表示,也不存在扩展整数类型,则该整数常量没有类型。


位精确整数类型是ISO/IEC 9899:2024标准新增内容。整数常量如果存在wbWBuwb或者UWB后缀,该整数常量是位精确整数类型。wbWB后缀对应的是_BitInt(N)类型;在能够容纳值位和符号位的情况下,N为大于1的最小整数值;即使整数常量是正值,N也应该包含符号位。uwbUWB后缀对应的是unsigned _BitInt(N)类型;在能够容纳值位的情况下,N为大于0的最小整数值。

5WB   //_BitInt(4)类型,1个符号位,3个值位。
-5WB  //_BitInt(4)类型,1个符号位,3个值位。  
0X5WB //_BitInt(4)类型,1个符号位,3个值位。
5UWB  //unsigned _BitInt(3)类型,3个值位。