二进制文件读/ C来写 [英] Binary file reading/writing in C

查看:180
本文介绍了二进制文件读/ C来写的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我有一个包含以下内容的input.bin文件

  IK-SZH; jdl72u;李四; 2013年3月28日11:05
IK-GRR; kat91n;李四; 2013年3月21日15:41
IK-GRR; oat62f;李四; 2013年3月24日08:08

我在做什么是读取到一个结构。做一些东西与数据。添加/删除线。
然后,我想结构的内容写回input.bin文件相同的格式同上。

但是,而不是表现为它的上方。是这样的(无空格):

  IK-SZH NUL jdl72u NUL李四NUL NUL NUL NUL NUL 2013年3月28日NUL NUL NUL IK-GRR NUL kat91n NUL李四NUL NUL NUL NUL ...

当我重新读取文件(使用完全无效)只放1号线到结构

我的code

  typedef结构{富
    孩子的char [7];
    炭JID [7];
    焦炭名[21];
    炭时间[20];}富;富富[200];
FILE * FP;
INT大小;

-------文件阅读

 无效读取(字符*文件名){
    FP = FOPEN(文件名,RB);
    INT I = 0;    而(!的feof(FP)){        如果(FP == NULL){PERROR(文件打开错误。\\ n);出口(1);}        的fscanf(FP,%[^;];%[^;];%20 [^ \\];%S \\ n,foo的[I] .kid,富[I] .jid,
                富[I] .name和富[I]。时间);
        我++;
    }    大小=我;    打印();    FCLOSE(FP);
}
无效的print(){
    INT I;
    对于(i = 0; I<大小; ++ I){
        的printf(%S \\ t%S \\ t%S \\ t%S \\ n,foo的[I] .kid,富[I] .jid,
               富[I] .name和富[I]。时间);
    }
}

-----作家

 无效的write(){
    焦炭海峡[1000];    FILE * F =的fopen(input.bin,世行);
    fseek的(F,0,SEEK_SET);
    INT I;
    对于(i = 0; I< jel_size;我++)
            FWRITE(安培; foo的[I]的sizeof(结构富),1,F);
    FCLOSE(F);}

想这一点,但这并没有写入任何文件:

 字符海峡[1000];
    sprintf的(STR,%S,%S,%S,%S \\ n,jelent [I] .kazon,
                    jelent [I] .jazon,jelent [I] .nev,jelent [I] .ido);        写(F,放大器;海峡,sizeof的(STR))!= sizeof的(STR);


解决方案

您的结构定义是:

  typedef结构美孚
{
    孩子的char [7];
    炭JID [7];
    焦炭名[21];
    炭时间[20];
}富;

在code写入结构的文件在的write()

 为(i = 0; I< jel_size;我++)
    FWRITE(安培; foo的[I]的sizeof(结构富),1,F);

如果所述结构与所有字节零intialized,则用于数据的第一行你提到:

  IK-SZH; jdl72u;李四; 2013年3月28日11:05

我们可以推断,该结构包含:

  IK-SZH \\ 0
jdl72u \\ 0
李四\\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0 \\ 0
2013年3月28日11:05 \\ 0 \\ 0 \\ 0 \\ 0

这或多或少同意你说的话该文件包含:

  IK-SZH NUL jdl72u NUL李四NUL NUL NUL NUL NUL 2013年3月28日NUL NUL NUL

据我估计,你的名字,时间和日期后的NUL后失踪了几个完全无效。

如果你想文本输出,你将不得不在格式化数据的write()使用 fprintf中()类似于您在阅读()函数有的fscanf()语句。你应该从函数返回一个状态,以表明它是否成功。你可以争辩的检查 FCLOSE()成功了。

 无效写入(无效)
{
    FILE *计划生育=的fopen(input.bin,W);
    如果(FP!= 0)
    {
        的for(int i = 0; I< jel_size;我++)
            fprintf中(FP,%S;%S;%;%S \\ n,foo的[I] .kid,富[I] .jid,富[I] .name和富[I]。时间);
        FCLOSE(FP);
    }
}

如果你想二进制输出,你应该使用二进制输入阅读()。同样,你应该考虑返回成功或失败的指示;避免全局变量也好。

 无效读(为const char *文件名)
{
    FILE *计划生育=的fopen(文件名,RB);
    如果(FP!= 0)
    {
        对于(I = 0;的fread(安培; foo的[I],sizeof的(富[I]),1,FP)== 1;我+ +)
            ;
        FCLOSE(FP);
        大小=我;
    }
}

这两种方法都能正常工作;试图用一个在输出和其它输入会导致混乱和混淆。

请注意,其功能阅读()的write()使用POSIX通过使用不同的接口。当你坚持使用标准的C,名字是公平供您使用,但您可能会与替代的名称,如阅读()和<$ C更好$ C>作家()或 foo_read() foo_write()

So I have an input.bin file which contains the following

IK-SZH;jdl72u;John Doe;2013-03-28 11:05
IK-GRR;kat91n;Jane Doe;2013-03-21 15:41
IK-GRR;oat62f;Jane Doe;2013-03-24 08:08

What I am doing is to read it into a struct. Doing some stuff with the data. Add/Delete lines. Then i would like to write the content of the structure back to the input.bin file in the same format as above.

But instead of appearing as it is above. It's like this (no spaces):

IK-SZH NUL jdl72u NUL John Doe NUL NUL NUL NUL NUL 2013-03-28 NUL NUL NUL IK-GRR NUL kat91n NUL Jane Doe NUL NUL NUL NUL ...

When I re-read the file (with the NULs) It only puts the 1st line into the struct

My code

typedef struct foo {
    char kid[7];    
    char jid[7];    
    char name[21];  
    char time[20];  

} Foo;

Foo foo[200];
FILE* fp;
int size;

------- File reader

void read(char* filename){
    fp = fopen(filename, "rb"); 
    int i = 0;

    while (!feof(fp)) {

        if (fp==NULL){perror("File opening error\n"); exit(1);}

        fscanf(fp,"%[^;]; %[^;]; %20[^\;]; %s\n", foo[i].kid, foo[i].jid,
                foo[i].name, foo[i].time);
        i++;
    }

    size = i;

    print();

    fclose(fp);
}


void print(){
    int i;
    for (i = 0; i < size; ++i){
        printf("%s\t %s\t %s\t %s\n", foo[i].kid, foo[i].jid,
               foo[i].name, foo[i].time);
    }
}

----- Writer

void write(){
    char str[1000];

    FILE* f = fopen("input.bin", "wb");
    fseek(f, 0, SEEK_SET);
    int i;
    for (i = 0; i < jel_size; i++)
            fwrite(&foo[i], sizeof(struct foo), 1, f);
    fclose(f);

}

Tried this, but this didn't write anything to the file:

    char str[1000];
    sprintf(str,"%s;%s;%s;%s\n", jelent[i].kazon,
                    jelent[i].jazon,jelent[i].nev,  jelent[i].ido );

        write(f,&str,sizeof(str))!=sizeof(str);

解决方案

Your structure definition is:

typedef struct foo
{
    char kid[7];    
    char jid[7];    
    char name[21];  
    char time[20];  
} Foo;

The code that writes the structures to the file is in write():

for (i = 0; i < jel_size; i++)
    fwrite(&foo[i], sizeof(struct foo), 1, f);

If the structures are intialized with all bytes zero, then for the first row of data you mention:

IK-SZH;jdl72u;John Doe;2013-03-28 11:05

we can infer that the structure contains:

IK-SZH\0
jdl72u\0
John Doe\0\0\0\0\0\0\0\0\0\0\0\0\0
2013-03-28 11:05\0\0\0\0

which more or less agrees with what you say the file contains:

IK-SZH NUL jdl72u NUL John Doe NUL NUL NUL NUL NUL 2013-03-28 NUL NUL NUL 

By my reckoning, you're missing a few NULs after the name and the time and one NUL after the date.

If you want text output, you will have to format the data in write() using fprintf() analogous to the fscanf() statement you have in the read() function. You should probably return a status from the function to indicate whether it was successful. You can argue for checking that fclose() was successful, too.

void write(void)
{
    FILE *fp = fopen("input.bin", "w");
    if (fp != 0)
    {
        for (int i = 0; i < jel_size; i++)
            fprintf(fp, "%s;%s;%;%s\n", foo[i].kid, foo[i].jid, foo[i].name, foo[i].time);
        fclose(fp);
    }
}

If you want binary output, you should use binary input in read(). Again, you should consider returning an indication of success or failure; avoiding global variables is good, too.

void read(const char *filename)
{
    FILE *fp = fopen(filename, "rb"); 
    if (fp != 0)
    {
        for (i = 0; fread(&foo[i], sizeof(foo[i]), 1, fp) == 1; i++)
            ;
        fclose(fp);
        size = i;
    }
}

Either technique will work; trying to use one on output and the other on input is going to lead to chaos and confusion.

Note that functions read() and write() are used by POSIX with a different interface. While you stick with Standard C, the names are fair for you to use, but you'd probably be better off with alternative names, such as reader() and writer() or foo_read() and foo_write().

这篇关于二进制文件读/ C来写的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆