在 C++ 中 memcpy'ing std::string
memcpy'ing std::string in C++
对于 Eigen 矩阵库,有人提交了以下问题:
https://forum.kde.org/viewtopic.php?f=74&t=140169
据我了解,问题是您不能对两个 std::strings.
进行基于 memcpy 的交换
在这里进行 memcpy 似乎并不可取,但我也不明白记者指出的问题。
似乎如果 std::string 在概念上是:
class string
{
union
{
class heap_str_
{
char* str_;
size_t len_;
}
char small_str[16];
}
};
我认为这两个在 memcpy 下都可以(?)(无法承受所有权问题,我想 'okay' 交换)。
我在这里错过了什么?
该错误包含以下详细信息:
internal data was not invariant of the storage location (storing an offset into this).
这会立即推翻你的假设。
结构可能看起来大致如下:
class string
{
char* str_;
union
{
size_t len_;
char small_str[16];
};
};
这样就可以访问 str_
,而无需在每次访问时检查 SSO。
问题是 SSO 对 memcpy
不安全,因为指向数据的指针通常被重定向到对象堆栈部分内的内部缓冲区。因此,当对象被复制到新位置时,指针仍然指向旧对象内部的(旧的,可能不再有效的)位置。
当然,std::string
(以及所有非 POD 类型)通常不应首先 memcpy
,尤其是当涉及堆分配时,因为它有风险,在至少,双重删除或堆损坏。
所以不,你不应该,永远,永远 memcpy
非 POD。即使你认为你 should/need 到。使用 std::copy
或想出其他办法。
对于 Eigen 矩阵库,有人提交了以下问题:
https://forum.kde.org/viewtopic.php?f=74&t=140169
据我了解,问题是您不能对两个 std::strings.
进行基于 memcpy 的交换在这里进行 memcpy 似乎并不可取,但我也不明白记者指出的问题。
似乎如果 std::string 在概念上是:
class string
{
union
{
class heap_str_
{
char* str_;
size_t len_;
}
char small_str[16];
}
};
我认为这两个在 memcpy 下都可以(?)(无法承受所有权问题,我想 'okay' 交换)。
我在这里错过了什么?
该错误包含以下详细信息:
internal data was not invariant of the storage location (storing an offset into this).
这会立即推翻你的假设。
结构可能看起来大致如下:
class string
{
char* str_;
union
{
size_t len_;
char small_str[16];
};
};
这样就可以访问 str_
,而无需在每次访问时检查 SSO。
问题是 SSO 对 memcpy
不安全,因为指向数据的指针通常被重定向到对象堆栈部分内的内部缓冲区。因此,当对象被复制到新位置时,指针仍然指向旧对象内部的(旧的,可能不再有效的)位置。
当然,std::string
(以及所有非 POD 类型)通常不应首先 memcpy
,尤其是当涉及堆分配时,因为它有风险,在至少,双重删除或堆损坏。
所以不,你不应该,永远,永远 memcpy
非 POD。即使你认为你 should/need 到。使用 std::copy
或想出其他办法。