简体   繁体   English

为什么fgets将光标移到下一行?

[英]Why fgets takes cursor to next line?

I have taken a string from the keyboard using the fgets() function. 我已经使用fgets()函数从键盘上提取了一个字符串。 However, when I print the string using printf() , the cursor goes to a new line. 但是,当我使用printf()打印字符串时,光标将移至新行。

Below is the code. 下面是代码。

#include<stdio.h>
int main()
{
    char name[25];

    printf("Enter your name: ");
    fgets(name, 24, stdin);
    printf("%s",name);

    return 0;
}

And below is the output. 下面是输出。

-bash-4.1$ ./a.out
Enter your name: NJACK1 HERO
NJACK1 HERO 
-bash-4.1$

Why is the cursor going to the next line even though I have not added a \\n in the printf() ? 即使我没有在printf()添加\\n ,光标为何仍会转到下一行?

However, I have noticed that if I read a string using scanf() , and then print it using printf() (without using \\n ), the cursor does not go to next line. 但是,我注意到,如果我使用scanf()读取字符串,然后使用printf()打印它(不使用\\n ),则光标不会移至下一行。

Does fgets() append a \\n in the string ? fgets()是否在字符串中附加\\n If it does, will it append \\0 first then \\n , or \\n first and then \\0 ? 如果这样做,将追加\\0第一则\\n\\n ,然后再\\0

The reason printf is outputting a newline is that you have one in your string. printf输出换行符的原因是您的字符串中有一个换行符。

fgets is not "adding" a newline --- it is simply reading it from the input as well. fgets不是在“添加”换行符,而是从输入中读取它。 Reading for fgets stops just after the newline (if any). 在换行符之后(如有) 将停止读取fgets

Excerpt from the manpage , emphasis mine: 摘自手册页 ,重点煤矿:

The fgets() function reads at most one less than the number of characters specified by size from the given stream and stores them in the string str. fgets()函数从给定的流中读取的字符数最多少于大小指定的字符数,并将它们存储在字符串str中。 Reading stops when a newline character is found, at end-of-file or error. 找到换行符时,文件末尾或错误时,读取停止。 The newline, if any, is retained. 换行符(如果有)将保留。 If any characters are read and there is no error, a `\\0' character is appended to end the string. 如果读取了任何字符且没有错误,则在字符串末尾附加一个'\\ 0'字符。

An easy way to check if there's a newline is to use the help of one of my favorite little-known functions --- strcspn() : 检查是否有换行符的一种简单方法是使用我最喜欢的鲜为人知的功能之一strcspn()

size_t newline_pos = strcspn(name, "\r\n");
if(name[newline_pos])
{
    /* we had a newline, so name is complete; do whatever you want here */
    //...

    /* if this is the only thing you do
       you do *not* need the `if` statement above (just this line) */
    name[newline_pos] = 0;
}
else
{
    /* `name` was truncated (the line was longer than 24 characters) */
}

Or, as an one-liner: 或者,单线:

// WARNING: This means you have no way of knowing if the name was truncated!
name[strcspn(name, "\r\n")] = 0;

Because if there is a '\\n' in the read text it will be taken by fgets() , the following was extracted from the 1570 draft §7.21.7.2 ¶ 2 因为如果有一个'\\n'在读取文本应当采取fgets()下面是从1570草案提取§7.21.7.2¶2

The fgets function reads at most one less than the number of characters specified by n from the stream pointed to by stream into the array pointed to by s. fgets函数从stream指向的流到s指向的数组中读取的字符数最多少于n指定的字符数。 No additional characters are read after a new-line character (which is retained) or after end-of-file. 在换行符(保留)或文件结束之后,不会读取其他字符。 A null character is written immediately after the last character read into the array. 在将最后一个字符读入数组后,立即写入空字符。

I highlighted by making bold the part which says that the '\\n' is kept by fgets() . 我通过将表示'\\n'fgets()保留的部分加粗来突出显示。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM