【问题标题】:int x; scanf() with %d and printf() with %c诠释 x; scanf() 与 %d 和 printf() 与 %c
【发布时间】:2017-07-15 23:43:14
【问题描述】:

int x; 因此变量将有 2 个字节的内存。 现在,如果我输入 66 并且因为 scanf() 带有 %d,66 将存储在 2 个字节的内存中,因为变量被声明为 int。

现在在带有 %c 的 printf() 中,应该只从一个字节的内存中收集数据来显示。

但是 %c 通过从内存中获取正确的数据 66 来正确显示 B。

为什么 %c 不只是从一个字节中获取数据?

【问题讨论】:

  • 请注意,int 必须至少 16 位宽,但可能而且通常更宽....
  • 大胆猜测,您的 int 被隐式转换为 char,保持值 66,适合 char 的 8 位。没有 MCVE,就不可能更精确。
  • @Yunnosch - 不需要 MCVE - 此行为已明确定义。
  • "它 %c 不只是从一个字节中获取数据吗?" --> 它获取 2(或 4)个字节,然后忽略除 1 之外的所有字节进行打印。

标签: c format-specifiers conversion-specifier


【解决方案1】:

%c 期望 int 参数,因为 默认参数提升 用于可变参数函数。换句话说,以下所有内容都是完全等价的:

int x = 66;
char y = 66;
printf("%c", x);         // A
printf("%c", (char)x);   // B
printf("%c", y);         // C
printf("%c", (int)y);    // D

所以发生的只是printfint 值 66 解释为 ASCII 码1 并打印相应的字符。


1。请注意,ASCII 在技术上是实现定义的设计决策。只是一个非常常见的。

【讨论】:

    【解决方案2】:

    printf() 语句中的%c 转换说明符需要int 参数。此外,由于printf() 是一个可变参数函数,因此char 将通过the default argument promotions 转换为int

    传递给printf()int 参数对应于%c 说明符,然后在打印之前由printf() 提供converted to an unsigned charNote that the conversion of a signed integer type to an unsigned integer type is well-defined in C,不涉及收集“仅来自一个字节的数据”。相反,如果新类型可以保持原始值,则该值保持不变;否则,大于新类型最大值的 1 将被添加到(或从中减去)旧 (signed) 值。例如,int 的值-1 将转换为-1 + 256255unsigned char 值(假设UCHAR_MAX 为255),它在unsigned char 的范围内。

    请注意,int 的值为 66 在转换为 unsigned char 时将保持不变,因为 66 正好在 unsigned char 的范围内。 UCHAR_MAX 必须最少为 255。

    【讨论】:

    • OP 在哪里提到他将char 传递给printf
    • @chqrlie——据我所知,无处;只需添加有关为什么printf() 需要int 的详细信息,但通常会使用%c 转换说明符传递char
    • 好点。更令人困惑的是,'a' 实际上是 C 中的 int(与 ++ 不同)。
    • @chqrlie——这也是一个好点,字符常量一开始就是int类型。难怪这些东西让学习者有点困惑?
    • 'A' 实际上是 C 中的一个 int 我知道。我认为等于 65 并作为二进制代码的 8 0 和 1 的相应二进制值组合保存在内存中。
    【解决方案3】:

    无论参数如何传递,%c 格式说明符总是在打印之前将其参数转换为 unsigned char。所以,%c 总是打印一个字节。

    您断言%c 从多个字节获取数据是没有根据的。给出的示例没有显示任何相反的证据 - 66 是一个适合一个字节的数字。

    可变参数传递的复杂性(是的,它作为int 传递)与在这种情况下观察到的行为无关。

    【讨论】:

    • 我可能是错的,但似乎 OP 认为 %c 期望 char,并且对实际参数比 char 更宽时可能发生的情况感到困惑;因此我试图描述发生的事情。也许也对整数类型的表示感到困惑......
    • 是的,先生。当实际参数大于 char 大小(即一个字节)时,我对可能发生的情况感到困惑。那么超过一个字节的数据应该到内存的哪里呢?因为只有一个字节与 char 变量相关。
    • 我知道 char 实际上只是一个整数
    • 但是char二进制码的内存大小只有一个字节
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-11-19
    • 2010-11-12
    • 1970-01-01
    • 2019-04-22
    • 1970-01-01
    • 2011-01-18
    • 2020-12-28
    相关资源
    最近更新 更多