【C语言入门教程】2.5 字符型数据

时间:2020-12-02 17:34:59

字符型数据用于在计算机上保存字符编码和一些文本控制命令,多个字符型数据和字符串结束符组成的序列称为字符串。Linux 系统与其他大多数操作系统一样,支持 ASCII编码对字符编码,每个字符占用 1 个字节的存储空间。

2.5.1 字符常量

字符常量是指用一对单引号包围起来的一个字符,例如'c','3','%'。字符常量中的单引号只起定界作用并不表示字符本身。单引号中的字符不能是单引号和反斜杠“\”,他们必须用转义字符表示。

每个字符在 ASCII 编码里有唯一的整数值,例如 0 的值为 0x30,A 的值为 0x41。因此,两个字符常量间的运算,或字符常量与整型变量间的运算是允许的,代码如下:

short a, b;			// 声明短整型变量
a = 'c' + '1'; // 将两个字符常量相加,并将结果保存到短整型变量 C 中
b = '9' - 9; // 计算字符常量 9 与整型常量 9 之间的差,为变量 b 赋值

上例中,变量 a 的值 0x94,变量 b 的值为 0x30。

2.5.2 字符串常量

字符串常量是指用一对双引号包围起来的一串字符。例如"China"、"886000"等都是字符串常量。双引号只起定界作用,其中不能包含双引号,字符串也不能是唯一一个反斜杠。例如“"”和“\”是非法的。

C语言中,字符串常量存储在内存中时,系统自动在字符串的末尾加一个字符串结束符,即 ASCII中编码为0的字符NULL,常用“\0” 表示。因此,在程序中,长度为n个字符的字符串常量,在内存中占有 n+1 个字节的存储空间。

例如,字符串“China”有 5 个字符,作为字符串“China”存储在内存中时,共占 6 个字节,系统自动在后面加上NULL字符,其存储形式如下表所示:

ASCII码     0x43 0x68 0x69 0x6E 0x61 0x00
字符 C h i n a \0

要特别注意“字符常量”与“字符串常量”的区别,除了表示形式不同外,其存储性质也不相同,字符 A 只占 1 个字节,而字符串 A 却占 2 个字节。

2.5.3 转义字符

转义字符用于表示C语言中有特殊意义的符号,或者 ASCII码字符集中无法显示的控制符号。例如,单引号和双引号,以及换行符、字符串、字符串结束符。转义字符用反斜杠加上一个字符组成,也可用该字符的ASCII码来代替字符的意义。例如\0用于表示字符串结束符,\n 表示换行符。下表给出了C语言中常用的转义字符。

C语言中常见的转义字符
转义字符 说明 ASCII码
\a 响铃 0x07
\b 退格 0x08
\f 换页 0x0C
\n 换行 0x0A
\r 回车 0x0D
\t 水平制表 0x09
\\ 反斜杠 0x5C
\? 问号字符 0x3F
\' 单引号 0x27
\" 双引号 0x22
\0 NULL 0x00

在C语言中使用转义字符\ddd或者\xhh可以方便灵活地表示任意字符。\ddd为斜杠后面 3 位八进制数,这 3 位八进制数的值即为对应的八进制ASCII码。\xhh后面跟 2 位十六进制数,这 2 位十六进制数即为对应的十六进制ASCII码值。

2.5.4 符号常量

使用预处理命令#define定义的常量称为符号常量。为了在程序中易于区别,符号常量通常使用大写英文字母作为标识符。定义的形式是:

#define <符号常量名> <常量>

其中,符号常量名遵循 C 语言标识符的定义方法,常量值可以是任何基本数据类型。如下例所示:

#define EV 2.78				// 定义表示数值的符号常量
#define BJ "BeiJing" // 定义表示字符串的符号常量

符号常量的作用是提高程序的易读性,便于程序的设计和调试。如果某一数值或字符串在程序中使用次数较多,或者代表特定的意义,那么将其定义为符号常量。如果该数值或字符串需要修改,只需要对预处理命令中定义的常量值进行修改即可。

2.5.5 字符变量

字符变量用来存放ASCII码符号,一次只能存放一个符号,因为单个字符变量的存储空间只有 1 字节。字符变量的定义形式如下:

char c;			// 声明字符变量
c = 'm'; // 用字符常量给字符变量赋值

另外,给字符变量赋值也可以直接使用 ASCII码值,例如:

c = 0x6D;        // 直接使用ASCII码值给字符变量赋值

与字符常量一样,字符变量也可以进行数学运算。通过查阅 ASCII码表,可以发现大写字母码值与小写字母之间的差为 0x20,即 A 加上 0x20 的结果为 a。当字符变量进行数值运算时,给字符变量赋的值大于字符变量的值域,会产生周期性变化。如下例源代码所示:

char c1, c2, c3;			// 声明字符变量
c1 = 357; // 使用值域范围外的数值为字符变量赋值
c2 = -251; // 使用值域范围外的数值为字符变量赋值
c3 = 'm' + 256; // 表达式的计算结果在字符串变量值域以外
printf("%d, %d, %d\n", c1, c2, c3); // 将字符变量中储存的数值以十进制数输出

在 C 语言里,这个程序是正确的,3 个变量中储存的十进制数值分别是 101、5、109。变量 c1 的值等于 357 减去 256,c2 的值是 -251 加上 256,c3 的值加上 256 后并未变化,变量越界时呈现出周期性变化。产生周期性的原因在于计算机底层的数值表示方法,所有数值都被保存为二进制,而数值超过值域后产生的高位数值被省略。例如变量 c3 的二进制值为 01101101,当它加上 256 后,计算机需要 2 个字节来保存计算结果 00000001 01101101。而字符变量的存储空间只有1 字节,所以前面的高位数值被省略,计算结果与原值相同。这一特性也是所有整型变量都具备的。