我很难弄清楚为什么这段代码不能正常工作。我正在学习I / O操作的基础知识,我必须想出一个C程序,它在'log.txt'文件中写入从标准输入中给出的内容,并且当输入'stop'字时,程序必须停止
所以我的代码是:
#include "main.h"
#define SIZE 1024
int main(int argc, char *argv[])
{
int fd;
int readBytes;
int writBytes;
char *buffer;
if ((fd = open("log.txt", O_WRONLY|O_APPEND)) < 0)
{
perror("open");
}
buffer = (char *) calloc (SIZE, sizeof(char));
while ((readBytes = read(0, buffer, SIZE) < SIZE)&&(strncmp(buffer, "stop", 4) != 0));
if ((writBytes = write(fd, buffer, SIZE)) < 0)
{
perror("write");
}
if ((close(fd)) < 0)
{
perror("close");
}
}
如果我输入:
this is just a text
stop
输出
stop
is just a text
如果我输入的不仅仅是一句话:
this is just a text
this is more text
and text again
stop
这是记录的内容:
stop
ext again
xt
t
最重要的是,如果我尝试从vim或只是文本编辑器编辑log.txt文件,我可以看到'\ 00'。我猜\ 00代表1024可用的所有剩余字节,对吧?我该如何防止这种情况发生?
答案 0 :(得分:2)
看起来你期待
readBytes = read(0, buffer, SIZE) < SIZE)
以某种方式积累缓冲区中的东西。它没有。每个后续的read
都会将它在缓冲区开头读取的内容放入其中,覆盖之前read
已读取的内容。
您需要将write
放在while
块中 - 每次阅读都写一次,而write
只需要read
,否则你会写日志文件中的垃圾(来自calloc
的零和/或上一次读取的剩余部分)。
另请注意,尽管您的技术大部分时间都可能用于行缓冲输入流,但如果从文件或管道重定向,它将无法满足您的预期效果。您应该使用格式化的输入函数(例如getline
,如果您的实现有scanf
或fgets
)。