do-while循环中scanf()的行为未定义

dced5bon  于 2023-02-21  发布在  其他
关注(0)|答案(3)|浏览(130)

我现在正在看一本书《C编程现代方法》学习C语言,遇到了这个代码。当我试图运行它时,在连续键入“abc”这样的字符并点击Enter(新行)后,什么也没有打印出来。请解释一下这是怎么回事。

char ch;
do {
    scanf("%c" , &ch);
} while (ch != '\n');
printf("%c", ch);
ht4b089n

ht4b089n1#

你要求用户使用scanf输入一个字符,这是在一个循环中发生的,* 直到 * 用户输入一个'\n'或换行符(与按回车键相同),这时循环将中断。
然后,print语句将打印变量ch中的字符,此时该字符为'\n'(因为该变量只存储一个字符,即您键入的最后一个字符)。
这个换行符在你运行程序的时候可能是看不见的,所以你可能看不到它。你可以在循环后添加另一个print语句,如果这个print语句是从一个换行符开始的,你就知道'\n'被打印到了前一行。
比如:

#include <stdio.h>

int main()
{
    char ch;
    do 
    {
        scanf("%c" , &ch);
    } while (ch != '\n');
    
    printf("%c", ch);
    printf("I should show up on a newline");
    
    return 0;
}
sycxhyv7

sycxhyv72#

您提供的代码使用scanf()函数从输入中读取字符,并将其存储在变量ch中,直到遇到换行符(\n)为止。之后,程序打印读取的最后一个字符,即换行符。
当你输入一个换行符后,你看不到任何输出的原因是因为printf()语句只在循环结束后执行,所以程序等待你输入一个换行符来终止循环,并打印最后一个读取的字符。
如果你想看到你输入的字符,你可以在循环中添加一个printf()语句,如下所示:

char ch;
do {
    scanf("%c" , &ch);
    printf("%c", ch);
} while (ch != '\n');

这将打印出从输入中读取的每个字符,因此您可以看到您正在键入的内容。

qkf9rpyu

qkf9rpyu3#

当我试图运行它时,在键入像abc这样的连续字符并点击Enter(新行)后,什么也没有打印出来。
对于发布的代码,如果循环结束,scanf("%c", &ch)读取并存储到ch中的最后一个字节是换行符,因此printf("%c", ch)输出这个换行符,看起来 * nothing * 没有打印出来,但实际上有东西,换行符在终端上是不可见的,但会将光标移动到下一行。
您可以通过将printf调用更改为以下内容来使其更加明确:

printf("last value: '%c'\n", ch);

但是请注意,建议不要使用发布的代码来读取输入流的内容:

  • 如果流位于文件末尾,则scanf("%c", &ch)可能无法读取字节。如果无法测试此条件,则会导致未定义的行为(ch未修改,因此如果输入流为空文件,则保持未初始化状态)或无限循环,因为ch可能永远不会接收到换行符。
  • 这段代码是一个典型的do/while的例子,有一个典型的bug。2用getchar()和一个while循环来写代码会更好。

以下是修改后的版本:

#include <stdio.h>

int main(void) {
    int c;         // must use int to distinguish EOF from all valid byte values
    int count = 0; // to tell whether a byte was read at all
    char ch = 0;   // the last byte read

    // read all bytes from the input stream until end of file or a newline
    while ((c = getchar()) != EOF && c != '\n') {
        ch = (char)c;
        count++;
    }
    if (count == 0) {
        printf("no characters entered: ");
        if (c == EOF) {
            printf("end of file or read error\n");
        } else {
            printf("empty line\n");
        }
    } else {
        printf("last character on line is '%c'\n", ch);
        if (c == EOF) {
            printf("end of file or input error encountered\n");
        }
    }
    return 0;
}

相关问题