fclose返回值检查
是否需要检查fclose的返回值?如果我们成功地打开了一个文件,那么它无法关闭的可能性有多大 谢谢 问候,,fclose返回值检查,c,file-io,C,File Io,是否需要检查fclose的返回值?如果我们成功地打开了一个文件,那么它无法关闭的可能性有多大 谢谢 问候,, Jay当您将fwrite写入文件时,它可能不会实际写入任何内容,它可能会保留在缓冲区中(文件对象内部)。调用fflush实际上会将其写入磁盘该操作可能会失败,例如,如果磁盘空间不足,或者存在其他一些I/O错误 fclose也会隐式刷新缓冲区,因此它可能会由于相同的原因而失败。手册页指出,它可能会由于close或fflush可能会失败的任何原因而失败 引述: 如果出现以下情况,close(
Jay当您将
fwrite
写入文件时,它可能不会实际写入任何内容,它可能会保留在缓冲区中(文件对象内部)。调用fflush
实际上会将其写入磁盘该操作可能会失败,例如,如果磁盘空间不足,或者存在其他一些I/O错误
fclose
也会隐式刷新缓冲区,因此它可能会由于相同的原因而失败。手册页指出,它可能会由于close或fflush可能会失败的任何原因而失败
引述:
如果出现以下情况,close()系统调用将失败:
[EBADF] fildes is not a valid, active file descriptor.
[EINTR] Its execution was interrupted by a signal.
[EIO] A previously-uncommitted write(2) encountered an
input/output error.
fflush可能会失败,原因是()会失败,基本上是在您无法实际写入/保存文件的情况下。如果在应用程序的上下文中,如果fclose()失败,您可以想出一些有用的方法,然后测试返回值。如果不能,请不要。您必须始终检查fclose()的结果。fclose可能失败的一个原因是,是否仍有任何数据被缓冲,并且隐式fflush失败。我建议始终调用fflush并在那里执行任何错误处理。我已经多次看到fclose()返回非零 经过仔细检查,发现真正的问题在于书写,而不是fclose 由于正在写入的内容在实际写入之前被缓冲,当调用fclose()时,所有缓冲区都被刷新。所以,在fclose()期间,写入缓冲suff时出现任何问题,比如磁盘已满。正如David Yell所说的,为了编写一个防弹应用程序,你需要考虑fCutele()的返回值。 你可以(并且应该)报告错误,但从某种意义上说, 在调用fclose()之后,流的任何使用都会导致未定义的行为
fclose()
将在返回之前刷新任何未写入的输出(通过fflush()
),因此在fwrite()
或fprintf()
时不会报告基础write()
产生的错误,但在执行fclose()
时不会报告。因此,write()
或fflush()
可以生成的任何错误都可以由fclose()
生成fclose()。如果NFS服务器崩溃,则close()
将失败,因此fclose()
也将失败。其他网络文件系统可能也是如此
假设您正在生成数据。您从文件中获取了旧数据,然后对数据进行一些处理,生成更多数据,然后将其写入新文件。您要小心不要覆盖旧文件,因为您知道尝试创建新文件可能会失败,并且希望在这种情况下保留旧数据(有些数据总比没有数据好)。在完成所有成功的
fwrite()
之后(因为您仔细检查了fwrite()
的返回值),您将fclose()
文件。然后,您可以rename()
您刚刚编写的文件并覆盖旧文件
如果fclose()
由于写入错误(磁盘已满?)而失败,那么您只是用一些可能是垃圾的内容重写了上一个好文件。哎呀
因此,如果它很关键,您应该检查fclose()
的返回值
在代码方面:
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
FILE *ifp = fopen("in.dat", "rb");
FILE *ofp = fopen("out.dat", "wb");
char buf[BUFSIZ];
size_t n;
int success = 1;
if (ifp == NULL) {
fprintf(stderr, "error opening in.dat\n");
perror("in.dat");
return EXIT_FAILURE;
}
if (ofp == NULL) {
fclose(ifp);
fprintf(stderr, "error opening out.dat\n");
perror("out.dat");
return EXIT_FAILURE;
}
while ((n = fread(buf, 1, sizeof buf, ifp)) > 0) {
size_t nw;
if ((nw = fwrite(buf, 1, n, ofp)) != n) {
fprintf(stderr, "error writing, wrote %lu bytes instead of %lu\n",
(unsigned long)n,
(unsigned long)nw);
fclose(ifp);
fclose(ofp);
return EXIT_FAILURE;
}
}
if (ferror(ifp)) {
fprintf(stderr, "ferror on ifp\n");
fclose(ofp);
fclose(ifp);
return EXIT_FAILURE;
}
#ifdef MAYLOSE_DATA
fclose(ofp);
fclose(ifp);
rename("out.dat", "in.dat"); /* Oops, may lose data */
#else
if (fclose(ofp) == EOF) {
perror("out.dat");
success = 0;
}
if (fclose(ifp) == EOF) {
perror("in.dat");
success = 0;
}
if (success) {
rename("out.dat", "in.dat"); /* Good */
}
#endif
return EXIT_SUCCESS;
}
#包括
#包括
内部主(空)
{
文件*ifp=fopen(“in.dat”、“rb”);
文件*ofp=fopen(“out.dat”、“wb”);
char buf[BUFSIZ];
尺寸;
int成功=1;
如果(ifp==NULL){
fprintf(stderr,“在.dat中打开时出错\n”);
perror(“in.dat”);
返回退出失败;
}
如果(ofp==NULL){
fclose(ifp);
fprintf(stderr,“打开.dat时出错”);
perror(“out.dat”);
返回退出失败;
}
而((n=fread(buf,1,sizeof buf,ifp))>0){
西北尺寸;
如果((nw=fwrite(buf,1,n,ofp))!=n){
fprintf(stderr,“写入错误,写入了%lu字节而不是%lu\n”,
(无符号长)n,
(无符号长)西北);
fclose(ifp);
fclose(ofp);
返回退出失败;
}
}
中频(铁磁(ifp)){
fprintf(标准,“ifp上的ferror\n”);
fclose(ofp);
fclose(ifp);
返回退出失败;
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
FILE *ifp = fopen("in.dat", "rb");
FILE *ofp = fopen("out.dat", "wb");
char buf[BUFSIZ];
size_t n;
int success = 1;
if (ifp == NULL) {
fprintf(stderr, "error opening in.dat\n");
perror("in.dat");
return EXIT_FAILURE;
}
if (ofp == NULL) {
fclose(ifp);
fprintf(stderr, "error opening out.dat\n");
perror("out.dat");
return EXIT_FAILURE;
}
while ((n = fread(buf, 1, sizeof buf, ifp)) > 0) {
size_t nw;
if ((nw = fwrite(buf, 1, n, ofp)) != n) {
fprintf(stderr, "error writing, wrote %lu bytes instead of %lu\n",
(unsigned long)n,
(unsigned long)nw);
fclose(ifp);
fclose(ofp);
return EXIT_FAILURE;
}
}
if (ferror(ifp)) {
fprintf(stderr, "ferror on ifp\n");
fclose(ofp);
fclose(ifp);
return EXIT_FAILURE;
}
#ifdef MAYLOSE_DATA
fclose(ofp);
fclose(ifp);
rename("out.dat", "in.dat"); /* Oops, may lose data */
#else
if (fclose(ofp) == EOF) {
perror("out.dat");
success = 0;
}
if (fclose(ifp) == EOF) {
perror("in.dat");
success = 0;
}
if (success) {
rename("out.dat", "in.dat"); /* Good */
}
#endif
return EXIT_SUCCESS;
}