【发布时间】:2011-04-07 22:41:11
【问题描述】:
我正在为 c++ 寻找一种非常快速的二进制序列化技术。我只需要序列化对象中包含的数据(没有指针等)。我希望它尽可能快。如果它是特定于 x86 硬件的,那是可以接受的。
我熟悉执行此操作的 C 方法。作为测试,我已经对几种技术进行了基准测试。我发现 C 方法比我实现的最佳 C++ 方法快 40%。
关于如何改进 C++ 方法(或执行此操作的库)的任何建议?内存映射文件有什么好的吗?
// c style writes
{
#pragma pack(1)
struct item
{
uint64_t off;
uint32_t size;
} data;
#pragma pack
clock_t start = clock();
FILE* fd = fopen( "test.c.dat", "wb" );
for ( long i = 0; i < tests; i++ )
{
data.off = i;
data.size = i & 0xFFFF;
fwrite( (char*) &data, sizeof(data), 1, fd );
}
fclose( fd );
clock_t stop = clock();
double d = ((double)(stop-start))/ CLOCKS_PER_SEC;
printf( "%8.3f seconds\n", d );
}
大约 1.6 秒的测试 = 10000000
// c++ style ofstream writes
// define a DTO class
class test
{
public:
test(){}
uint64_t off;
uint32_t size;
friend std::ostream& operator<<( std::ostream& stream, const test& v );
};
// write to the stream
std::ostream& operator<<( std::ostream &stream, const test& v )
{
stream.write( (char*)&v.off, sizeof(v.off) );
stream.write( (char*)&v.size, sizeof(v.size) );
return stream;
}
{
test data;
clock_t start = clock();
std::ofstream out;
out.open( "test.cpp.dat", std::ios::out | std::ios::trunc | std::ios::binary );
for ( long i = 0; i < tests; i++ )
{
data.off = i;
data.size = i & 0xFFFF;
out << data;
}
out.close();
clock_t stop = clock();
double d = ((double)(stop-start))/ CLOCKS_PER_SEC;
printf( "%8.3f seconds\n", d );
}
大约 2.6 秒的测试 = 10000000
【问题讨论】:
-
这不是序列化,而是内存转储。如果您的对象的内存布局发生变化,或者如果您从大端平台传递到小端平台,则它不起作用。
-
那不等于代码。在 operator
-
@Matthieu:(来自维基百科)序列化:“序列化是将数据结构或对象转换为位序列以便可以存储在文件或内存缓冲区中的过程”。似乎符合使用该定义的条件。我真的不需要担心不同架构之间的互操作性。
-
@Dead:你不需要打包类,因为成员是分开写的。使用 C++ 可以像使用 C 结构一样使用类吗?
-
@Paul:“C++ 流非常慢。” - 但并非如此。在这种情况下,C++ 实现显然低于标准,但性能应该与 C 变体一样好。这也可能是由于
iostream与stdio中的默认缓冲设置不同。
标签: c++ serialization