c - K&R(第二版)中没有出现在任何勘误表中的可能的新错误?

标签 c

我想我在 K&R(第二版)中发现了一个新的错误。

  • 第 164 页写道,如果发生“文件结束”,“feof”将返回非零值。

  • 在第 170 页,写到“读取”在到达“文件末尾”时返回 0。

  • 在页面 176 K&R , 上面写着“feof”的定义。

  • 在页面 178 K&R ,我觉得“_fillbuf”定义中用红色下划线标注的两个条件应该是相反的。

我说得对吗?

最佳答案

我同意 Bjorn Acommentlurkercomment — 我没有发现代码有问题。

feof()的规范p164 上的内容对应于 C 标准所说的内容——尽管我已经链接到 POSIX 规范,但它旨在与 C 标准相匹配。规范说 read()返回0表示EOF;如果它返回 -1,则表示有一个错误,而不是简单的 EOF。这么多是没有争议的。

请注意,p176 上的feof() 的实现;它不是 feof() 的实现。尽管最终结果非常相似,但还有其他实现在细节上与此不同。

#define feof(p)  (((p)->flag & _EOF) != 0)

宏无异常(exception);如果在标志中设置了 _EOF 位,则返回 1,否则返回 0 — 这符合预期(要求)。

在 p178 上留下了 _fillbuf() 的示例实现。相关代码为:

fp->cnt = read(fp->fd, fp->ptr, bufsize);
if (--fp->cnt < 0) {
    if (fp->cnt == -1)
        fp->flag |= _EOF;
    else
        fp->flag |= _ERR;
    fp->cnt = 0;
    return EOF;
}
return (unsigned char)*fp->ptr++;

需要考虑三种情况:

  • read() 返回一个正数
  • read() 返回零
  • read() 返回一个负数

在第一种情况下,代码递减 fp->cnt 至少为 0 因此执行最终返回;返回一个字符,正确转换为 unsigned char 以确保该值为正数。

在第二种情况下(EOF处理),代码将fp->cnt0递减到-1,然后进入正文外部 if 语句。由于 fp->cnt 当前为 -1,它设置 fp->flag 中的 _EOF 位和计数归零并报告 EOF。这是正确的。

在第三种情况下(错误处理),代码将 fp->cnt-1 递减到 -2,然后进入外部 if 语句的主体。由于 fp->cnt 不是 -1,它设置 fp->flag 中的 _ERR 位和计数归零并报告 EOF。这也是正确的。

因此,K&R 第 2 版中的代码是正确的 — 您没有发现以前未报告的错误。

关于c - K&R(第二版)中没有出现在任何勘误表中的可能的新错误?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45392360/

相关文章:

c - 如何通过 C 库获取 Linux 硬件和系统信息?

c - 这种悲伤教导的奇怪行为的原因是什么?

c - luaL_openlibs 的隐式声明

c - 无法将 ip 地址从字符串复制到 sockaddr_in

c - qsort 一个指向结构体指针数组的双指针

c++ - 如何在 C/C++ 中包含宏的行的末尾添加语句?

c - 为什么要阻止文件作为控制终端打开(使用 O_NOCTTY)?

C: 如何使用 main argv 的参数打开文件?

c - 将单个值分配给多个变量

c - c中减少字符串长度,错在哪里?