从指针指向内存的二进制文件中读取结构

read structure from binary file having pointer pointed to memory

struct st {
        char *p;
        int len;
};

这是我需要写入二进制文件的结构,以及保存在

中的字符串

char *p

我应该用字符数组数据写一个二进制文件。写入二进制文件后。也应该能够从二进制文件中以相同的结构读取它。

我尝试使用 FSEEK_END 获取二进制大小,并根据文件大小执行 fread,但它没有保存字符串。请建议。任何 help/suggestion/pointer 将不胜感激。

提前致谢。

示例代码:

 struct st {
         char *p;
         int len; 
 };

 struct st varr;
 varr.len = 100;
 varr.p = new char[gen];
 strcpy(varr.p, "Hello World");

 FILE *p;
 p=fopen("address","wb");
 fwrite(&varr,sizeof(struct st),1,p);
 fclose(p); 

这会把指向二进制文件的指针写给我。但我想在这里写整个字符串,但重点是,它应该用一个 fwrite 完成。

将其写入二进制文件是没有用的。一个文本文件就足够了。

但是,如果这是你的家庭作业(或如此),我建议你按照以下步骤进行:

  • 将长度写成整数;

  • 写入字符串的 len 个字节。这不包括终止空值。

回读时:

  • 读取整数长度;

  • 分配这个长度的内存加一个字节

  • 将字符串读入该内存并添加终止空值

用这个长度和指向已分配内存的指针填充您的结构。


在你的评论中,你不断迭代你想要一步到位地阅读和写作。 用你当前的数据结构是不可能的因为字符串总是在内存中的其他地方并且fwrite只能写入一个连续的内存块。

但是,您是否会将数据结构更改为:

struct st{
    char p[128];
    int len;
};

然后你 可以 一次写入和读取,因为现在结构是一个连续的内存块。但是现在字符串被限制为这 128 个字节(或您制作的任何大小)。

我建议先保存 strlen(p),然后保存 char *p 指向的所有字符。如果您尝试按原样 fwrite 结构,您将最终(在文件中)得到地址的值,并将其重新分配到第一个字符。您不想保存第一个字符的地址,是吗?

如果您非常担心没有两个 fwrite 您可以使用零长度数组的包装器结构。

 struct st_wrap {
         int len; 
         char p[0];
 };

struct st_wrap *temp= malloc (sizeof (struct st_wrap ) + strlen(varr.p)+1);
temp->len = strlen(varr.p);

//Copy the data
strcpy(temp->p,varr.p);

//Then write it to file
fwrite(temp,sizeof(struct st_wrap)+strlen(varr.p),1,p);

假设您已经将长度和字符串写入二进制文件:

FILE* fp = fopen("file.bin", "wb");

/* writing */
st str = { .p = "foo", .len = 3 };
fwrite((char*)(&str.len), sizeof(str.len), sizeof(str.len), fp);
fwrite(str.p, str.len, str.len, fp);

您现在可以(在不同的上下文中)将文件中的内容读取到结构对象中:

FILE* fp = fopen("file.bin", "rb");
st str;
/* read length */
fread((char*)&str.len, sizeof(str.len), sizeof(str.len), fp);
/* allocate enough space */
str.p = malloc((str.len + 1) * sizeof(char));
/* read string */
fread(str.p, str.len + 1, str.len + 1, fp);

记得在完成后释放内存 p:

free(str.p);

我尝试了很多方法,@kiran Biradar 的回答对我帮助很大。因此在这里显示工作代码。

WriteBinaryFile.cpp

    struct st_wrap {
            int len;
            int crc;
            char p[0]; 
    };


    int main ()
    {
            char p[100] = "Hello World";
            struct st_wrap *temp= (struct st_wrap*) malloc (sizeof (struct st_wrap ) + strlen(p)+1);
            temp->len = strlen(p);
            temp->crc = 400;
            strcpy(temp->p,p);
            cout << temp->p << endl;
            cout << temp->len << endl;
            cout << temp->crc << endl;

            FILE *p1;
            p1=fopen("binary.dat","wb");
            fwrite(temp,sizeof(struct st_wrap)+strlen(p),1,p1);
            fclose(p1);

    }

ReadBinaryFile.cpp

struct st_wrap {
        int len;
        int crc;
        char p[0];
};


int main ()
{
        struct st_wrap *vw;
        FILE *f=fopen("binary.dat","rb");
        fseek(f, 0, SEEK_END);
        long int filesize = ftell(f);
        fseek(f, 0, SEEK_SET);
        vw = (struct st_wrap*) malloc (filesize);
        fread(vw,filesize,1,f);
        cout << vw->len << endl;
        cout << vw->p << endl;
        cout << vw->crc << endl;
        return 0;
}