C FGET无法读取换行符

C FGET无法读取换行符,c,file,fgets,scanf,C,File,Fgets,Scanf,如果FGET读取一个空行,我想在这两个变量中存储两个零。但是它失败了,永远不要执行if块代码。fgets应该如何读取空行?c不是单个字符;它是指向字符序列的指针。您的if询问此位置是否与您用换行符预先填充的位置相同,如果这样描述,显然永远不会成功 如果要查看c指向的第一个字符是否为换行符,请使用If(*c=='\n')c不是单个字符;它是指向字符序列的指针。您的if询问此位置是否与您用换行符预先填充的位置相同,如果这样描述,显然永远不会成功 如果要查看c指向的第一个字符是否为换行符,请使用If(

如果FGET读取一个空行,我想在这两个变量中存储两个零。但是它失败了,永远不要执行if块代码。fgets应该如何读取空行?

c
不是单个字符;它是指向字符序列的指针。您的
if
询问此位置是否与您用换行符预先填充的位置相同,如果这样描述,显然永远不会成功


如果要查看
c
指向的第一个字符是否为换行符,请使用
If(*c=='\n')
c
不是单个字符;它是指向字符序列的指针。您的
if
询问此位置是否与您用换行符预先填充的位置相同,如果这样描述,显然永远不会成功


如果要查看
c
指向的第一个字符是否为换行符,请使用
If(*c=='\n')

好的,有几点:

1.功能行为 从函数:

C库函数
char*fgets(char*str,int n,FILE*stream)
从指定的流中读取一行,并将其存储到str指向的字符串中。当读取(n-1)个字符、读取换行符或到达文件结尾时(以先到者为准),该函数停止

与man fgets相同:

fgets()从流中最多读入一个小于大小的字符,并将它们存储到s指向的缓冲区中。EOF或换行符后,读取停止。如果新行被读取,它将被存储到缓冲区中。终止的空字节('\0')存储在缓冲区中最后一个字符之后

这意味着什么:
fgets
遇到
\n
(新行)字符后停止读取。但让我们看看我们可以对结果字符串做什么:

假定
fgets
在最多读取N-1个字符后停止,您知道,如果
strlen(c)
为499,则可能不会遇到EOF/EOL字符。
如果
fgets
遇到下线,它将返回一个
NULL
指针,因此您可以使用该指针。除此之外,以下是如何找到新行:

考虑到
c
是一个数组,我还避免在声明和
fgets
调用中硬编码缓冲区的大小。相反,我会使用:

char c[500];
fgets(c, 500, fp);

if (c == "\n") {
    customer.checkoutTime = 0;
    customer.payment = 0;
}
我添加了
*check='\0'
检查,以响应chux的一条注释,以防
fgets
实际从文件中读取nul字符。因为您只对以
\n
开头的行感兴趣,所以只需跳过这样的行即可


2.代码问题 除此之外,您发布的代码:

char c[500], // perhaps a macro here?
    *check;
//more code
check = fgets(c, sizeof c, fp); // fgets returns relevant stuff
if (check == NULL || *check == '\0')
    //Nothing was read (EOL), or an error occurred,
    //or fgets read a nul-character at the start of the line
if (strlen(c) == (sizeof c) -1)
    //likely no EOL
else
    c[strlen(c) - 1] most likely to be EOL
这在几个层面上都是错误的
“\n”
生成指向只读字符串(
char*
)的指针,该字符串永远不会等于
c
。使用strcmp比较字符串。对于字符,请使用单引号,要比较
c
中的值,必须取消对其的引用:

if (c == "\n") {
在对Scott Hunter答案的评论中,您提到您正在使用
*c=='\n'
进行检查,这很好,但该表达式中的
c
会衰减为指向数组中第一个元素的指针(即
fgets
读取的第一个字符)。这个角色不太可能成为新台词

基本上,您正在编写
c[0]='\n'
,而您应该查看最后一个字符(
c[strlen(c)-1]='\n'
),以查看您读取的字符串是否以新行结尾

3.Windows线条端点: 大多数系统对新行使用
\n
。Windows使用
\r\n
fgets
实际上会在
\n
字符上拾取,但缓冲区不会为空。
c
的值实际上是:

if (c[i] == '\n') // or *c == '\n'
因此字符串中的第一个字符将不匹配
\n
。您没有指定编码和使用的系统(也没有指定编译器),但请确保在需要时修剪任何前导的回车字符

这里有更多的细节

这可能意味着,从代码的角度来看,您认为为空的行不会以
\n
开头,而是以
\r
开头。请尝试检查以下内容:

c[500] = {'\r', '\n', 0};

好的,有几件事:

1.功能行为 从函数:

C库函数
char*fgets(char*str,int n,FILE*stream)
从指定的流中读取一行,并将其存储到str指向的字符串中。当读取(n-1)个字符、读取换行符或到达文件结尾时(以先到者为准),该函数停止

与man fgets相同:

fgets()从流中最多读入一个小于大小的字符,并将它们存储到s指向的缓冲区中。EOF或换行符后,读取停止。如果新行被读取,它将被存储到缓冲区中。终止的空字节('\0')存储在缓冲区中最后一个字符之后

这意味着什么:
fgets
遇到
\n
(新行)字符后停止读取。但让我们看看我们可以对结果字符串做什么:

假定
fgets
在最多读取N-1个字符后停止,您知道,如果
strlen(c)
为499,则可能不会遇到EOF/EOL字符。
如果
fgets
遇到下线,它将返回一个
NULL
指针,因此您可以使用该指针。除此之外,以下是如何找到新行:

考虑到
c
是一个数组,我还避免在声明和
fgets
调用中硬编码缓冲区的大小。相反,我会使用:

char c[500];
fgets(c, 500, fp);

if (c == "\n") {
    customer.checkoutTime = 0;
    customer.payment = 0;
}
我添加了
*check='\0'
检查,以响应chux的一条注释,以防
fgets
实际从文件中读取nul字符。既然你在