普通旧数据和 std::memcpy 对齐问题
Plain Old Data and `std::memcpy` alignment issues
尝试响应 ,我提出了一个解决方案,使用 std::memcpy()
将泛型类型存储在 char
的缓冲区中。
我怀疑存储 POD 可能存在内存对齐问题(我知道使用非 POD 类型,如 std::string
,非常非常危险)。
简而言之:以下程序存在内存对齐问题?
如果是,是否可以编写安全的类似内容(将 POD 值存储在 char
缓冲区中)?又如何?
#include <cstring>
#include <iostream>
int main()
{
char buffer[100];
double d1 { 1.2 };
std::memmove( buffer + 1, & d1, sizeof(double) );
double d2;
std::memmove( & d2, buffer + 1, sizeof(double) );
std::cout << d2 << std::endl;
return 0;
}
这是安全的。
[basic.types]/2:
For any trivially copyable type T
, if two pointers to T
point to distinct T
objects obj1
and obj2
, where
neither obj1
nor obj2
is a base-class subobject, if the underlying bytes (1.7) making up obj1
are copied
into obj2
, obj2
shall subsequently hold the same value as obj1
.
由于 double
可简单复制,因此您的代码定义明确。
您可以在未对齐的缓冲区之间进行复制。您不能做的是将缓冲区转换为 double * 然后直接对内存中的值进行操作,作为 double。由于对齐问题,这通常会导致错误。
尝试响应 std::memcpy()
将泛型类型存储在 char
的缓冲区中。
我怀疑存储 POD 可能存在内存对齐问题(我知道使用非 POD 类型,如 std::string
,非常非常危险)。
简而言之:以下程序存在内存对齐问题?
如果是,是否可以编写安全的类似内容(将 POD 值存储在 char
缓冲区中)?又如何?
#include <cstring>
#include <iostream>
int main()
{
char buffer[100];
double d1 { 1.2 };
std::memmove( buffer + 1, & d1, sizeof(double) );
double d2;
std::memmove( & d2, buffer + 1, sizeof(double) );
std::cout << d2 << std::endl;
return 0;
}
这是安全的。
[basic.types]/2:
For any trivially copyable typeT
, if two pointers toT
point to distinctT
objectsobj1
andobj2
, where neitherobj1
norobj2
is a base-class subobject, if the underlying bytes (1.7) making upobj1
are copied intoobj2
,obj2
shall subsequently hold the same value asobj1
.
由于 double
可简单复制,因此您的代码定义明确。
您可以在未对齐的缓冲区之间进行复制。您不能做的是将缓冲区转换为 double * 然后直接对内存中的值进行操作,作为 double。由于对齐问题,这通常会导致错误。