C写入文件忽略换行?
C writing into files ignores new line?
鉴于以下代码,我有:printf("hello\n");
所以我希望在 myfile
中看到 hello\n
。但是当我 运行 我的程序时,我看到 haha
这意味着 \n
被忽略了,这是为什么?
值得注意: 当我用 printf("hellos");
替换 printf("hello\n");
时,我也没有看到 s
字母被打印出来。所以我想也许上面写着什么,但问题是谁以及为什么?
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/file.h>
#include <string.h>
int main() {
// creates a new file having full read/write permissions
int fd = open("myfile", O_RDWR | O_CREAT, 0666);
write(fd, "haha\n", 5);
close(fd); // line 6
fd = open("myfile", O_RDWR); // line 7
close(0);
close(1);
dup(fd);
dup(fd);
if (fork() == 0) {
char s[100];
dup(fd);
scanf("%s", s);
printf("hello\n");
write(2, s, strlen(s)); // line 18
return 0; // line 19
}
wait(NULL);
printf("Father finished\n");
close(fd);
return 0;
}
运行ning 后 myfile 的内容:
haha
helloFather finished (new line after this)
首先,行为未定义。您开始使用 stdout
引用与 stdin
相同的文件描述符,而无需在执行前关闭或刷新 stdin
。让我们尝试从 POSIX 2.5.1 Interaction of File Descriptors and Standard I/O Streams:
中获取重要的内容
[...] if two or more handles are used, and any one of them is a stream, the application shall ensure that their actions are coordinated as described below. If this is not done, the result is undefined.
[...]
For a handle to become the active handle, the application shall ensure that the actions below are performed between the last use of the handle (the current active handle) and the first use of the second handle (the future active handle). [...]
[...]
For the first handle, the first applicable condition below applies. [...]
[...]
If the stream is open with a mode that allows reading and the underlying open file description refers to a device that is capable of seeking, the application shall either perform an fflush(), or the stream shall be closed.
您的代码:
scanf("%s", s); // associates stdin with fd
// Ups - no flush(stdin) nor fclose(stdin)
printf("hello\n"); // associates stdout with fd - undefined behavior
您看到的结果来自 scanf
调用 ungetc
,它会增加文件位置,但也会“记住”在刷新流后取消增加文件位置。因为它在子进程终止时被刷新,文件位置递减,父进程覆盖子进程的最后一个字符。
鉴于以下代码,我有:printf("hello\n");
所以我希望在 myfile
中看到 hello\n
。但是当我 运行 我的程序时,我看到 haha
这意味着 \n
被忽略了,这是为什么?
值得注意: 当我用 printf("hellos");
替换 printf("hello\n");
时,我也没有看到 s
字母被打印出来。所以我想也许上面写着什么,但问题是谁以及为什么?
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/file.h>
#include <string.h>
int main() {
// creates a new file having full read/write permissions
int fd = open("myfile", O_RDWR | O_CREAT, 0666);
write(fd, "haha\n", 5);
close(fd); // line 6
fd = open("myfile", O_RDWR); // line 7
close(0);
close(1);
dup(fd);
dup(fd);
if (fork() == 0) {
char s[100];
dup(fd);
scanf("%s", s);
printf("hello\n");
write(2, s, strlen(s)); // line 18
return 0; // line 19
}
wait(NULL);
printf("Father finished\n");
close(fd);
return 0;
}
运行ning 后 myfile 的内容:
haha
helloFather finished (new line after this)
首先,行为未定义。您开始使用 stdout
引用与 stdin
相同的文件描述符,而无需在执行前关闭或刷新 stdin
。让我们尝试从 POSIX 2.5.1 Interaction of File Descriptors and Standard I/O Streams:
[...] if two or more handles are used, and any one of them is a stream, the application shall ensure that their actions are coordinated as described below. If this is not done, the result is undefined.
[...]
For a handle to become the active handle, the application shall ensure that the actions below are performed between the last use of the handle (the current active handle) and the first use of the second handle (the future active handle). [...]
[...]
For the first handle, the first applicable condition below applies. [...]
[...]
If the stream is open with a mode that allows reading and the underlying open file description refers to a device that is capable of seeking, the application shall either perform an fflush(), or the stream shall be closed.
您的代码:
scanf("%s", s); // associates stdin with fd
// Ups - no flush(stdin) nor fclose(stdin)
printf("hello\n"); // associates stdout with fd - undefined behavior
您看到的结果来自 scanf
调用 ungetc
,它会增加文件位置,但也会“记住”在刷新流后取消增加文件位置。因为它在子进程终止时被刷新,文件位置递减,父进程覆盖子进程的最后一个字符。