使用 fwrite 转储的文件是否可以跨不同系统移植?

发布于 2024-08-20 07:07:35 字数 429 浏览 14 评论 0原文

我可以假设使用 fwrite 生成并使用 fread 读取的文件可以跨不同系统移植吗? 32 位/64 位 Windows、OSX、Linux。

//dumping
FILE *of =fopen("dumped.bin","w");
double *var=new double[10];
fwrite(var, sizeof(double), 10,FILE);
//reading
file *fo=fopen()
double *var=new double[10];
fread(var,sizeof(double),10,of);

那么结构体呢

struct mat_t{
    size_t x;
    size_t y;
    double **matrix;
}

?它们是可移植的吗?

Can I assume a file generated with fwrite and read using fread is portable across different systems. 32bit/64bit windows,osx,linux.

//dumping
FILE *of =fopen("dumped.bin","w");
double *var=new double[10];
fwrite(var, sizeof(double), 10,FILE);
//reading
file *fo=fopen()
double *var=new double[10];
fread(var,sizeof(double),10,of);

And what about structs

struct mat_t{
    size_t x;
    size_t y;
    double **matrix;
}

Are these portable?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

囚我心虐我身 2024-08-27 07:07:35

简短回答:

详细回答:

您正在写出数据的二进制表示形式。
这不能跨平台、操作系统甚至编译器移植。

您编写的所有对象都有可以更改的内容:

int:        size and endianess.
double:     size and representation.
structure:  Each member has to be looked at individually.
            The structure itself may be padded different on different compilers.
            Or even the same compiler with different flags.
pointers:   Are meaningless even across processes on the same machine.
            All pointers have to be converted into something meaningful like
            a named object that is provided separately. The transport will then
            have to convert named objects into pointers at the transport layer
            at the destination.

您有两个主要选项:

  • 流式传输数据。
    这基本上是将结构转换为文本表示并发送字符串。对于小型对象,API 结构这是当前进行跨平台/语言通信的标准方法(尽管数据通常以 XML 或 Json 等格式包装)。
  • 转换为网络中立的二进制格式
    为此,我们有 htonl() 和函数族() 用于转换整数。双精度数更难,通常转换为两个整数(值取决于精度要求)。字符串被转换为长度,后跟字符序列等。然后每个字符串被单独写入流。这可以比流式传输更紧凑(因此更高效)。不利的一面是,您将两端紧密耦合到一种非常特定的格式,从而使解决方案特别脆弱,并且在错误情况下更难纠正。

Short Answer: NO

Long Answer:

You are writing out the binary representation of the data.
This is not portable across platforms or OS or even compilers.

All the objects you have written have things that can change:

int:        size and endianess.
double:     size and representation.
structure:  Each member has to be looked at individually.
            The structure itself may be padded different on different compilers.
            Or even the same compiler with different flags.
pointers:   Are meaningless even across processes on the same machine.
            All pointers have to be converted into something meaningful like
            a named object that is provided separately. The transport will then
            have to convert named objects into pointers at the transport layer
            at the destination.

You have two main options:

  • Streaming the data.
    This is basically converting the structure into a textual representation and sending the string. For small object, API structures this is current standard method of doing cross platform/language communication (though the data is usually wrapped in some format like XML or Json).
  • Convert to a network neutral binary format
    For this we have htonl() and family of functions() for converting integers. Doubles are harder and usually converted into two integers (the values depend on accuracy requirements). Strings are converted to a length followed by a sequence of characters etc. Then each is written individually to the stream. This can be much more compact than streaming (and thus efficient). The down side is that you are tightly coupling both ends to a very specific format and thus makes the solution particularly brittle and harder to correct in error situations.
对你再特殊 2024-08-27 07:07:35

fwritefread 具有很强的可移植性,但是您可能会遇到诸如 sizeof(double) 之类的问题,这些问题可能因系统而异。确保您编写的每个二进制字段都有一个定义的大小,该大小不依赖于编译器或操作系统 - 您可以通过使用显式给出其大小的类型(例如uint32_t)来很大程度上实现这一点。

您还必须担心字节顺序,但是您可以使用宏 ntohntohlhtonhtonl可以用来为您交换字节顺序,并且它们应该被定义为可以在您编译它们的任何系统上正常工作。

fwrite and fread are plenty portable, but you will have problems with things like sizeof(double), which may vary across systems. Make sure that every binary field you write has a defined size which isn't dependent on compiler or OS--you can largely accomplish this by using the types that explicitly give their size, such as uint32_t.

You also have to worry about endianness, but there are macros ntoh, ntohl, hton, and htonl that you can use to swap endianness for you, and they should be defined to work correctly for whatever system you compile them on.

抽个烟儿 2024-08-27 07:07:35

这个文件肯定是不可移植的。这就是为什么像 htons 这样的东西存在。您必须确保您的文件格式非常明确地指定大小和字节序。由于单个类型不可移植,结构体也不可移植(甚至不考虑结构打包)。

This file will definitely not be portable. That's why things like htons exist. You have to make sure your file format very clearly specifies size and endianness. Since the individual types aren't portable, structs aren't either (not even considering struct packing).

魔法唧唧 2024-08-27 07:07:35

如果您正在编写结构,并且它们不是独立的(意味着它们有指针、子结构),那么最好使用某种序列化库。有 Boost Serilization 库,它采用面向对象的方法。输出可以轻松地从文本切换为二进制,这使得调试变得更加容易。

还有 HDF5(分层数据格式),一组常用于科学计算的库在一些不寻常的硬件上(不是标准的 x86)。我从来没有使用过这个,所以我不能说它是多么容易使用,但可以处理巨大的数据集(多个 TB)。

If you are writing structures, and they are not self-contained (meaning they have pointers, sub-structures), you are much better off using some kind of serialization library. There is the Boost Serilization library, which takes an object-oriented approach. The output can be easily switched from text to binary, which makes debugging a lot easier.

There is also HDF5 (Hierarchical Data Format), a set of libraries that is routinely used in scientific computing on some unusual hardware (not your standard x86). I've never used this, so I can't speak to how easy it is to use, but will handle huge data sets (multiple TB).

长伴 2024-08-27 07:07:35

您忘记了 Windows 假定文件写入处于文本模式,因此您需要将 fwrite() 的第二个参数中的“w”更改为“wb”

You're forgetting Windows assumes file writes are in text mode, so you need to change the "w" to "wb" in the second parameter to fwrite()

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文