gpt4 book ai didi

c++ - 在 C++ 中制作可移植的字节序正确的文件读取/写入代码的简洁方法

转载 作者:搜寻专家 更新时间:2023-10-30 23:55:44 24 4
gpt4 key购买 nike

我想编写一些 C++ 代码,以字节序正确的方式从文件中读取和写入。更准确地说,我希望能够读取特定类型的文件,我可以轻松检测到其字节顺序(其魔数(Magic Number)是否被反转)。

但是我该如何正确地干净地读取文件呢?我已阅读以下文章,其中提供了一个有用的想法:

http://www.gamedev.net/page/resources/_/technical/game-programming/writing-endian-independent-code-in-c-r2091

这里的想法是创建一个类,其中有一些函数指针指向所需的字节顺序正确的 read() 函数。但根据我的经验,函数指针很慢,尤其是当你必须像本例那样频繁地调用它们时。另一种选择是有一个

if (file_was_detected_big_endian) { read_bigendian(); } else { read_littleendian(); }

对于我拥有的每一个 read_x_bit_int() 函数,但这似乎也很低效。

我正在使用 Boost,所以我可以利用它的所有优势来帮助我。特别是,有 endian 子库:

http://www.boost.org/doc/libs/develop/libs/endian/doc/buffers.html

虽然我不确定如何才能干净地使用这段代码来做我想做的事。我希望有一些代码,我可以在其中直接读取 16 个字节到代表文件一部分的 struct 的指针中,同时自动更正字节顺序。我当然可以自己编写这段代码,但我觉得一定已经存在可靠的解决方案。

我认为我所有的代码都将被手动填充并防止对齐问题。

谢谢!

最佳答案

因此 dasblinkenlight 提出的虚函数方法可能就足够了 - 特别是因为 I/O 可能会成为时间的主要消耗者。但是,如果您确实发现您的读取函数占用了大量 CPU 时间,您可以通过模板化文件读取器来摆脱虚函数调度。

这里有一些伪代码演示了这一点:

基本上,创建两个读取器类,一个用于每个字节序:

class LittleReader {
public:
LittleReader(std::istream& is) : m_is(is) {}
char read_char() {//read byte from m_is}
int read_int32() {//read 32-bit int and convert;}
float read_float()....
private:
std::istream& m_is;
};

class BigReader {
public:
BigReader(std::istream& is): m_is(is){}
char read_char(){...}
int read_int32(){..}
float read_float(){...}
private:
std::istream& m_is;
}

将阅读逻辑的主要部分(魔数(Magic Number)位除外)分离到一个函数模板中,该模板将上述类之一的实例作为参数:

template <class Reader>
void read_endian(Reader &rdr){
field1 = rdr.read_int32();
field2 = rdr.read_float();
// process rest of data file
...
}

从本质上讲,编译器将为您的 read_endian 函数创建两个实现 - 一个用于每个字节序。由于没有动态调度,编译器还可以内联所有对 read_int32、read_float 等的调用。

最后,在您的主要阅读器函数中,查看魔数(Magic Number)以确定要实例化哪种阅读器:

void read_file(std::istream& is){
int magic(read_magic_no(is));
if (magic == MAGIC_BIG_ENDIAN)
read_endian(BigReader(is));
else
read_endian(LittleReader(is));
}

此技术为您提供了灵 active ,而不会产生任何虚拟分派(dispatch)开销,但会增加(二进制)代码大小。如果您的循环非常紧凑并且您需要压榨每一滴性能,它会非常有用。

关于c++ - 在 C++ 中制作可移植的字节序正确的文件读取/写入代码的简洁方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30467973/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com