下面是我正在编译的代码:
#include <stdio.h>
void main()
{
printf("Hello%cWorld\n", 0);
}
以下是编译器输出:
HelloWorld
下面是 Bing chat-gpt 在创意模式下的相同输出
Copilot:
The output of printf("Hello%cWorld\n", 0) will be:
Hello
原因是 %c 格式说明符需要单个字符作为参数,但您提供了 0。这相当于空字符“ ”,它标记 C1 中字符串的结尾。因此,printf函数在遇到空字符后将停止打印字符串,并忽略其余字符。
要按原样打印整个字符串,您需要使用 %s 格式说明符,它需要一个字符串作为参数。例如:
printf("Hello%sWorld\n", "\0");
This will print:
Hello\0World
或者,您可以使用另一个反斜杠转义反斜杠字符,如下所示:
printf("Hello\\0World\n");
This will also print:
Hello\0World
你: 但是当我编译上面的代码时,它给了我输出 HelloWorld
副驾驶: 这很奇怪。您发布的代码应该发出警告并仅打印 Hello。你确定你编译了相同的代码吗?也许您有不同版本的编译器或标准库,以不同的方式处理空字符。你能告诉我你用来编译和运行代码的确切命令吗? 😊
你: 我已经使用 gcc main.c -o app 来编译
副驾驶: 我懂了。您是如何运行该应用程序的?您是否使用了任何命令行参数或输入重定向? 😊
你: 我使用 ./app 命令运行应用程序,我没有使用任何命令行参数或输入重定向
副驾驶: 我懂了。好吧,我不确定为什么你得到的输出与预期不同。根据 C 标准,带有空字符参数的 printf 的行为是未定义的1。这意味着不同的编译器或平台可能会以不同的方式处理它,并且不能保证一致性或正确性。也许您的编译器或平台对空字符有一些特殊处理,或者您遇到了一些内存损坏或其他错误。
为了避免此类问题,我建议您始终为 printf 函数使用有效参数,并遵循格式说明符的规则。您可以在本文中找到有关 printf 函数及其格式说明符的更多信息2。
我希望这有帮助。如果您还有其他问题,请随时问我。 😊
1:警告:格式字符串在字符串正文中包含“”[-Wformat]2:C 中的 printf - GeeksforGeeks
请注意 GCC 版本:
coder@069e69391cf2:~/project/Rough/programs/3$ gcc -v
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/lib/gcc/x86_64-linux-gnu/9/lto-wrapper
OFFLOAD_TARGET_NAMES=nvptx-none:hsa
OFFLOAD_TARGET_DEFAULT=1
Target: x86_64-linux-gnu
Configured with: ../src/configure -v --with-pkgversion='Ubuntu 9.2.1-9ubuntu2' --with-bugurl=file:///usr/share/doc/gcc-9/README.Bugs --enable-languages=c,ada,c++,go,brig,d,fortran,objc,obj-c++,gm2 --prefix=/usr --with-gcc-major-version-only --program-suffix=-9 --program-prefix=x86_64-linux-gnu- --enable-shared --enable-linker-build-id --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --libdir=/usr/lib --enable-nls --enable-bootstrap --enable-clocale=gnu --enable-libstdcxx-debug --enable-libstdcxx-time=yes --with-default-libstdcxx-abi=new --enable-gnu-unique-object --disable-vtable-verify --enable-plugin --enable-default-pie --with-system-zlib --with-target-system-zlib=auto --enable-multiarch --disable-werror --with-arch-32=i686 --with-abi=m64 --with-multilib-list=m32,m64,mx32 --enable-multilib --with-tune=generic --enable-offload-targets=nvptx-none,hsa --without-cuda-driver --enable-checking=release --build=x86_64-linux-gnu --host=x86_64-linux-gnu --target=x86_64-linux-gnu
Thread model: posix
gcc version 9.2.1 20191008 (Ubuntu 9.2.1-9ubuntu2)
printf("Hello%cWorld\n", 0)
这里 %c 期望匹配 int 参数。我需要知道为什么有两种不同的输出,即编译器打印
HelloWorld
和chat-gptHello
。
请帮忙解释一下这种行为?
谢谢。
这完全是因为 ChatGPT 是错误的并且不是事实信息的来源。 ChatGPT 在其使用条款中告诉您这一点:
输出可能并不总是准确的。您不应依赖我们服务的输出作为事实或事实信息的唯一来源,或作为专业建议的替代品。
和:
您接受并同意……您不会依赖输出作为真相或事实信息的唯一来源,或作为专业建议的替代品。
更进一步,
printf("Hello%cWorld\n", 0);
告诉printf
打印“Hello”,然后打印代码为0的字符,然后打印“World”和换行符。 0 字符被发送到终端,可能会导致不显示,因此“W”将立即出现在“o”之后。
当编译器解析
"Hello%cWorld\n"
并看到 %c
时,它不会获取提供的参数 0
,并将其插入那里,然后注意到,“哦,字符串在这里结束”。它继续解析,直到 format 字符串达到 \0
。
它输出的结果字符串将是
Hello\0World\n