以下程序是否为有效的C程序?
#include <stdio.h>
int main()
{
fwrite("x", 1, 1, stderr);
fflush(stderr);
fgetc(stderr);
fwrite("y", 1, 1, stderr);
return 0;
}
请注意,我尝试从stderr读取。
当我在Visual C ++ 2008中编译它并运行它时,我得到以下输出:
xy
这是有道理的。但是,当我将stderr重定向到文件(test.exe 2> foo.txt
)时,我得到了一个
“Debug Assertion Failed”窗口,显示消息:“Inconsistent Stream Count。连续读取和写入之间的刷新”。在读取和写入之间添加fflush
可以解决问题。
(这在调试版本中发生。在发布版本中,第二次写入静默失败)。
这种行为是否正确,或者这是编译器库错误?我无法找到任何描述何时读取或写入在C中是非法的规则。
答案 0 :(得分:3)
C99在7.19.5.3(fopen
)第6段中说:
当使用更新模式(
'+'
作为上述mode
参数值列表中的第二个或第三个字符)打开文件时,可以在关联的流上执行输入和输出。但是,如果没有对fflush
函数的干预调用,输出不应直接跟随输入,并且输入不应直接跟随输出而不干预对文件定位功能的调用,除非输入操作遇到文件结束。
恭喜您在实践中发现了这个角落案例。库实现是完全正确的,因为你违反了上面引用的 。
顺便说一句,从stderr
读取并不罕见。当stdin
和stdout
被重定向且没有终端可用时,这非常有用。虽然C99不保证它是可读的,但我记得在类似POSIX的系统中有些情况已经完成了。