C 中的字符常量和初始化
Character Constants and Initialization in C
我正在通过一本名为 'C Primer Plus' 的书学习 C 语言。目前,我正在阅读 C 数据类型(第 3 章)并有一个问题。
书上是这么写的
Character Constants and Initialization
[...] A single character contained between single quotes is a C character constant. [...] Because characters are really stored as numeric values, you can also use the numerical code to assign values. [...] Somewhat oddly, C treats character constants as type int rather than type char. For example, on an ASCII system with a 32-bit int and an 8-bit char, the code
char grade = 'B';
represents 'B' as the numerical value 66 stored in a 32-bit unit, but grade winds up with 66 stored in an 8-bit unit.
这部分我的理解是declare语句char grade = 'B';
会将其char变量和字符常量存储在两个地方,一个是32位单元的数值66和变量grade
在 8 位单元中使用 66。 (这有点令人困惑。)然后书中接下来的两句话是:
This characteristic of character constants makes it possible to define a character constant such as 'FATE', with four separate 8-bit ASCII codes stored in a 32-bit unit. However, attempting to assign such a character constant to a char variable results in only the last 8 bits being used, so the variable gets the value 'E'.
这里我的理解是,多字符常量是可以的,不像书上一开始给的定义。但是,他们在上一部分中提到的两个地方中只有一个是可能的。因为字符常量在C中是int
类型,这里int
是32位,所以'FATE'有4个字符,每个8位;因此,4 * 8 = 32。但是一个char变量只有8位space,所以只会存储最后一个字母。
并且,为了应用知识,我尝试了
/* test.c */
#include <stdio.h>
int main(void)
{
char grade = 'FATE';
printf("%d, %c", grade, grade);
return 0;
}
这在编译时给了我一些警告。警告是多字符字符常量和隐式常量转换溢出。
然后我尝试了 'FAT'、'FA' 和 'F'。只有 'F' 有效。
最后,我的问题是:
- 我对这本书的理解正确吗?使用字符常量初始化字符变量是否需要两个位置来保存其值?
- 如果我是对的,为什么要将数值和字符变量分开?它在调用时如何准确地分离和连接在一起?为什么需要两个地方?
- 如果我是对的,我的 test.c 是否因为我的笔记本电脑系统的
int
单元只有一个 8 位字节而导致多字符字符常量失败?
'B'
是一个 value 类型 int
,但它没有存储在任何地方,就像 42 没有存储在任何地方一样,它是一个数字.但是,如果您在纸上写 42 十进制,它将占用纸上 space 的 2 位数字。如果你有 42 个苹果,数字 42 不需要写下来,因此它不会消耗 space,但你仍然有 42 个苹果...
现在 char grade
是一个 对象 。 char
类型的整数值 - 小整数(通常是 -128 ... 127、0 ... 255)可以存储到 grade
.
对象就像纸质表格中的一个字段,您可以在其中写入一定长度的文本。表单上的 char
将足以 space 仅用于该范围内的数字。
由于 ASCII 'B'
的值为 66,因此它很方便地适合 char
.
的范围
int
类型的对象可以存储更大数量级的整数(可能是 -32768 ... 32767,或 -2147483648 ... 2147483647;即 实现定义).
然后我们来看看多字符常量。与书上的声明不同,C 标准声明 (C11 6.4.4.4p10)
[...] The value of an integer character constant containing more than one character (e.g., 'ab') [...] is implementation-defined. [...]
即一个实现(C 编译器)可以定义 FATE
的值,因为它看起来合适。作者错误地声称该值需要是 'F' * 16777216 + 'A' * 65536 + 'T' * 256 + 'E'
的值,但 C 标准不需要这样的东西。这就是为什么许多编译器会警告使用多字符常量的原因(在你的情况下你得到 "warning: multi-character character constant [-Wmultichar]")* - 因为它们不是 可移植的 即相同的代码在使用不同的编译器编译时将不会以相同的方式运行。
现在,我们假设 'FATE'
确实产生了那个数字,即 1178686533。现在 你 如何将这个数字 121686533 写在你所在字段的表单中只能写-128 ... 127之间的数字吗?同样,该行为是 实现定义的 。作者的实现将采用该数字模 256,这将导致 69
,这是 E
字母的 ASCII 代码,但确切的行为再次取决于编译器实现。
为了警告实现定义的行为,编译器吐出类似 warning: overflow in conversion from 'int' to 'char' changes value from '1178686533' to '69 '.
主要的收获是:如果您打算将单词 FATE
的最后一个字母存储在 char grade
中,您可以这样做:
char grade = 'E';
作者这样做的方式可能会导致某些编译器将作者的书评分为 F
...
- 计算机只会识别二进制码,字符常量不会存储在两处,因为它们在计算机中是相同的二进制码
- 同上。
- 计算机把字符常量看成int类型,但实际上是按char大小的一个字节存储的,所以只存一个字节(你的计算机是F,当然是以二进制形式存储的) .打印时,%c 告诉计算机将内容输出为一个字符,最后显示的是 F。
我的英文不是很好。欢迎讨论。
首先需要了解字面量constants.Often,我们用一个后缀来告诉计算机这个字面常量属于什么类型的字面常量。
喜欢,123
10LLU
999L
。
字符常量是文字常量之一。
C把所有的字符常量都当作int
类型来处理(但还没有真正存储到内存中)。而变量声明的类型决定了存储的大小space.
char c = 'abc';
计算机认为abc
是int类型,但是char只有一个字节大小,所以最后存储的是'c'(或'a',取决于你的编译器)
printf("%c", character);
最后,C 将所有文字常量视为int
类型(或unsigned int,long int ....)。但是,但是存储的细节仍然取决于声明的类型。
我正在通过一本名为 'C Primer Plus' 的书学习 C 语言。目前,我正在阅读 C 数据类型(第 3 章)并有一个问题。
书上是这么写的
Character Constants and Initialization
[...] A single character contained between single quotes is a C character constant. [...] Because characters are really stored as numeric values, you can also use the numerical code to assign values. [...] Somewhat oddly, C treats character constants as type int rather than type char. For example, on an ASCII system with a 32-bit int and an 8-bit char, the code
char grade = 'B';
represents 'B' as the numerical value 66 stored in a 32-bit unit, but grade winds up with 66 stored in an 8-bit unit.
这部分我的理解是declare语句char grade = 'B';
会将其char变量和字符常量存储在两个地方,一个是32位单元的数值66和变量grade
在 8 位单元中使用 66。 (这有点令人困惑。)然后书中接下来的两句话是:
This characteristic of character constants makes it possible to define a character constant such as 'FATE', with four separate 8-bit ASCII codes stored in a 32-bit unit. However, attempting to assign such a character constant to a char variable results in only the last 8 bits being used, so the variable gets the value 'E'.
这里我的理解是,多字符常量是可以的,不像书上一开始给的定义。但是,他们在上一部分中提到的两个地方中只有一个是可能的。因为字符常量在C中是int
类型,这里int
是32位,所以'FATE'有4个字符,每个8位;因此,4 * 8 = 32。但是一个char变量只有8位space,所以只会存储最后一个字母。
并且,为了应用知识,我尝试了
/* test.c */
#include <stdio.h>
int main(void)
{
char grade = 'FATE';
printf("%d, %c", grade, grade);
return 0;
}
这在编译时给了我一些警告。警告是多字符字符常量和隐式常量转换溢出。
然后我尝试了 'FAT'、'FA' 和 'F'。只有 'F' 有效。
最后,我的问题是:
- 我对这本书的理解正确吗?使用字符常量初始化字符变量是否需要两个位置来保存其值?
- 如果我是对的,为什么要将数值和字符变量分开?它在调用时如何准确地分离和连接在一起?为什么需要两个地方?
- 如果我是对的,我的 test.c 是否因为我的笔记本电脑系统的
int
单元只有一个 8 位字节而导致多字符字符常量失败?
'B'
是一个 value 类型 int
,但它没有存储在任何地方,就像 42 没有存储在任何地方一样,它是一个数字.但是,如果您在纸上写 42 十进制,它将占用纸上 space 的 2 位数字。如果你有 42 个苹果,数字 42 不需要写下来,因此它不会消耗 space,但你仍然有 42 个苹果...
现在 char grade
是一个 对象 。 char
类型的整数值 - 小整数(通常是 -128 ... 127、0 ... 255)可以存储到 grade
.
对象就像纸质表格中的一个字段,您可以在其中写入一定长度的文本。表单上的 char
将足以 space 仅用于该范围内的数字。
由于 ASCII 'B'
的值为 66,因此它很方便地适合 char
.
int
类型的对象可以存储更大数量级的整数(可能是 -32768 ... 32767,或 -2147483648 ... 2147483647;即 实现定义).
然后我们来看看多字符常量。与书上的声明不同,C 标准声明 (C11 6.4.4.4p10)
[...] The value of an integer character constant containing more than one character (e.g., 'ab') [...] is implementation-defined. [...]
即一个实现(C 编译器)可以定义 FATE
的值,因为它看起来合适。作者错误地声称该值需要是 'F' * 16777216 + 'A' * 65536 + 'T' * 256 + 'E'
的值,但 C 标准不需要这样的东西。这就是为什么许多编译器会警告使用多字符常量的原因(在你的情况下你得到 "warning: multi-character character constant [-Wmultichar]")* - 因为它们不是 可移植的 即相同的代码在使用不同的编译器编译时将不会以相同的方式运行。
现在,我们假设 'FATE'
确实产生了那个数字,即 1178686533。现在 你 如何将这个数字 121686533 写在你所在字段的表单中只能写-128 ... 127之间的数字吗?同样,该行为是 实现定义的 。作者的实现将采用该数字模 256,这将导致 69
,这是 E
字母的 ASCII 代码,但确切的行为再次取决于编译器实现。
为了警告实现定义的行为,编译器吐出类似 warning: overflow in conversion from 'int' to 'char' changes value from '1178686533' to '69 '.
主要的收获是:如果您打算将单词 FATE
的最后一个字母存储在 char grade
中,您可以这样做:
char grade = 'E';
作者这样做的方式可能会导致某些编译器将作者的书评分为 F
...
- 计算机只会识别二进制码,字符常量不会存储在两处,因为它们在计算机中是相同的二进制码
- 同上。
- 计算机把字符常量看成int类型,但实际上是按char大小的一个字节存储的,所以只存一个字节(你的计算机是F,当然是以二进制形式存储的) .打印时,%c 告诉计算机将内容输出为一个字符,最后显示的是 F。 我的英文不是很好。欢迎讨论。
首先需要了解字面量constants.Often,我们用一个后缀来告诉计算机这个字面常量属于什么类型的字面常量。
喜欢,123
10LLU
999L
。
字符常量是文字常量之一。
C把所有的字符常量都当作int
类型来处理(但还没有真正存储到内存中)。而变量声明的类型决定了存储的大小space.
char c = 'abc';
计算机认为abc
是int类型,但是char只有一个字节大小,所以最后存储的是'c'(或'a',取决于你的编译器)
printf("%c", character);
最后,C 将所有文字常量视为int
类型(或unsigned int,long int ....)。但是,但是存储的细节仍然取决于声明的类型。