使用C ++中的fread从二进制文件中读取字符串及其长度

时间:2018-04-08 05:53:41

标签: c++ fwrite fread

Bellow你可以找到我用来将string_length写入二进制文件的代码片段,但代码不能按预期工作。写完之后我打开输出文件,字符串就在那里,但是当我从文件中读取字符串时,它会部分地读取字符串。似乎在读取string_length之后,文件指针寻找的内容超过它应该的数量,然后它错过了字符串的前8个字符!

#include <iostream>
#include <string>

FILE* file = nullptr;

bool open(std::string mode)
{
    errno_t err = fopen_s(&file, "test.code", mode.c_str());
    if (err == 0) return true;
    return false;
}

void close()
{
    std::fflush(file);
    std::fclose(file);
    file = nullptr;
}

int main()
{
    open("wb"); // open file in write binary mode

    std::string str = "blablaablablaa";

    auto sz = str.size();
    fwrite(&sz, sizeof sz, 1, file); // first write size of string
    fwrite(str.c_str(), sizeof(char), sz, file); // second write the string

    close(); // flush the file and close it

    open("rb"); // open file in read binary mode

    std::string retrived_str = "";

    sz = -1;
    fread(&sz, sizeof(size_t), 1, file); // it has the right value (i.e 14) but it seems it seeks 8 bytes more!
    retrived_str.resize(sz);
    fread(&retrived_str, sizeof(char), sz, file); // it missed the first 8 char

    close(); // flush the file and close it

    std::cout << retrived_str << std::endl;

    return 0;
}

PS:我删除了代码中的检查,以使其更具可读性。

2 个答案:

答案 0 :(得分:2)

您正在使用文件内容破坏retrieved_str对象,而不是将文件内容读入由retrieved_str控制的缓冲区。

fread(&retrived_str[0], 1, sz, file);

或者,如果您使用的是C ++ 17及其非常量std::string::data方法:

fread(retrived_str.data(), 1, sz, file);

答案 1 :(得分:1)

更改

fread(&retrived_str, sizeof(char), sz, file); // it missed the first 8 char

fread((void*)( retrived_str.data()), sizeof(char), sz, file); // set the data rather than the object