FILE流缓冲区如何工作?

时间:2018-01-09 12:52:00

标签: c buffer

我理解fopen()打开文件并为该文件的读写操作创建缓冲区。 fopen()返回该缓冲区的指针。

所以我的问题是,在下面的代码中,_copy函数正文有一个temp矩阵,可以在fread()fwrite()之间进行转换。为什么我不能直接从缓冲区转移到缓冲区?

/* example: copyfile.exe xxxxx.txt   zzzzzz.txt */
#include <stdio.h>
#include <stdlib.h>

#define BUFF 8192
void _copy(FILE *source, FILE *destination);

int main(int argc, char *argv[])
{
    FILE *fp1, *fp2;  // fp1 source file pointer// fp2 copied file pointer 

    if (argc !=3 )           //command line must have 3 arguments
    {
        fprintf(stderr, "Usage: %s (source file) (copy file)\n", argv[0][0]);
        exit(EXIT_FAILURE);
    }

    if ((fp1 = fopen(argv[1], "rb")) == NULL)    //Opening source file
    {
        fprintf(stderr, "Could not open %s\n",argv[1]);
        exit(EXIT_FAILURE);
    }
    if((fp2 = fopen(argv[2], "ab+")) == NULL)  //Opening destination file
    {
        fprintf(stderr, "could not create %s \n",argv[2]);
        exit(EXIT_FAILURE);
    }
    if( setvbuf(fp1,NULL, _IOFBF, BUFF) != 0) //Setting buffer for source file
    {
        fputs("Can't create output buffer\n", stderr);
        exit(EXIT_FAILURE);
    }
    if( setvbuf(fp2,NULL, _IOFBF, BUFF) != 0) //Setting buffer for destination file
    {
        fputs("Can't create input buffer\n", stderr);
        exit(EXIT_FAILURE);
    }


    _copy(fp1, fp2);  
    if (ferror(fp1)!=0)
        fprintf(stderr, "Error reading file %s\n", argv[1]);
    if(ferror(fp2)!=0)
        fprintf(stderr, "Error writing file %s\n",argv[2]);
    printf("Done coping %s (source) to %s (destination) \n",argv[1], argv[2]);
    fclose(fp1);
    fclose(fp2);
    return (0);
}

void _copy(FILE  *source, FILE *destination)
{
    size_t bytes;
    static char temp[BUFF];

    while((bytes = fread(temp,sizeof(char),BUFF,source))>0)
        fwrite(temp,sizeof(char),bytes,destination);
}

1 个答案:

答案 0 :(得分:1)

您不能在另一个FILE *中使用FILE *中的底层缓冲区。正如你在评论中被告知的那样,FILE *是一个不透明的指针。但是,您可以通过在非缓冲模式下强制两个文件来避免在缓冲区之间复制数据的开销:

setbuf(fp, NULL);   // cause the stream to be unbuffered