当使用和int来读取字符时,为什么值为4096 + ascii
我正在使用gcc并且正在测试使用整数或字符作为数据类型处理字符的各种方法。
int main() { int i; printf("Enter a char: "); scanf(" %c", &i); printf("integer value= %d char value=%c", i, i); return 0; }
输出:
输入char:f 整数值= 4198 char值= f
我很好奇存储的整数值。 看起来该值等于’f’的4096 + ascii值。
我的问题是为什么将4096添加到角色的ascii值? 这个价值代表什么?
输入以下程序,您就会明白原因:
#include int main (void) { int val = 4096; printf ("Enter your character: "); scanf ("%c",&val); printf ("integer val = %d, character val = %c\n", val, val); return 0; }
用gcc -Wall
(所有警告)编译它,给出:
qq.c: In function 'main': qq.c:6: warning: format '%c' expects type 'char *', but argument 2 has type 'int *'
(作为确保在编译时启用所有警告的任何理由)并运行它会得到与您找到的相同的结果:
Enter your character: f integer val = 4198, character val = f
这样做的原因是scanf
工作方式与变量在内存中的布局方式相结合。
scanf
只会获得一个字符并将其放入内存中。 因为你已经给它一个整数的地址,并且该整数是little-endian,它只会覆盖该整数的最低有效字节(LSB)。 考虑将该内存视为重叠区域,您将看到原因:
+--- The address passed to scanf. | V +------+ | char | <-- Treated as char. +------+------+------+------+ | lsb | | | msb | <-- Treated as integer (assumes 32-bit). +------+------+------+------+
因为scanf
没有触及整数的最右边的字节,所以它们留在调用之前的任何内容中。 在我的代码中,我明确强制到4096
但是,如果你的声明是未初始化的int val;
,内容将是不确定的。 事实上,当我删除初始化时,我得到1629542246
( 0x6120D766
,你仍然可以看到LSB设置为0x66
或f
)。
这只是意味着我的整数在scanf
调用之前看起来像这样:
+------+ | ?? | +------+------+------+------+ | ?? | d7 | 20 | 61 | +------+------+------+------+
而scanf
调用只改变了??
位。
你是否在读取char之前初始化int? 可能只是一个未初始化的价值。 你能展示代码吗? 使用什么函数将字符读入int?
4096是hex的0x00001000。 可以是字符之前或之后的标志或字符,或读取的字符数,具体取决于您用于阅读字符的内容。