下面的代码将stdout重定向到文件fname&然后重定向回原始标准输出。这对我来说可以。 但我无法理解它是如何运作的。如果有人能帮助我理解我将会相信它。
printf("\n This is console");
fflush(stdout);
fgetpos(stdout, &pos);
fd = dup(fileno(stdout));
freopen(fname, "a+", stdout);
printf("inside file op");
fflush(stdout);
dup2(fd,fileno(stdout));
close(fd);
clearerr(stdout);
fsetpos(stdout, &pos);
printf("\nBack to Console");
答案 0 :(得分:14)
让我们逐行完成。第一行打印的内容为stdout
:
printf("\n This is console");
然后它刷新stdout
,以便缓冲区中的所有剩余数据都被发送到stdout
,并且不会与文件数据混淆:
fflush(stdout);
现在我们将自己的当前位置存储在stdout
中,否则如果stdout
已经定向到文件,我们可能会(?)覆盖它的前面部分。
fgetpos(stdout, &pos);
现在我们克隆当前stdout
的文件描述符。由于我们即将更改stdout
指向的位置,因此我们需要保留原始副本:
fd = dup(fileno(stdout));
现在我们已经保留了所有内容,我们可以重新打开stdout
作为文件:
freopen(fname, "a+", stdout);
此时,stdout
已重定向到该文件。我们现在可以打印到它:
printf("inside file op");
现在我们已经完成了对文件的打印。我们需要刷新stdout
(现在是文件),这样就不会与正常的stdout
数据混淆:
fflush(stdout);
之后,我们将当前stdout
描述符上的原始stdout
文件描述符克隆。
dup2(fd,fileno(stdout));
现在可以关闭克隆的那个:
close(fd);
我不太确定为什么会这样,但是这会清除写入文件时发生的任何错误:
clearerr(stdout);
现在我们恢复stdout
的位置。同样,据我所知,这只有在最初被重定向到文件时才有用:
fsetpos(stdout, &pos);
现在我们又回到原来的stdout
,所以我们可以再次打印:
printf("\nBack to Console");