用于分配任意数量的字节和指针算术struct alignas(1) byte {};
安全吗?我更喜欢使用这种字节类型而不是 char 数组,因为字节需要转换为另一种类型才能使用。
快速使用示例:
#include <cstring>
#include <iostream>
struct alignas(1) byte {};
class Any
{
byte* mData;
public:
template<class T>
explicit Any(T pValue) : mData(new byte[sizeof(T)]) {
std::memcpy(mData, &pValue, sizeof(T));
}
~Any() {
delete[] mData;
}
template<class T>
auto get() -> T& {
return *(T*)(mData);
}
};
int main()
{
int i = 5;
Any a(i);
std::cout << a.get<int>() << std::endl;
}
不能分配 4 个字节,然后将第一个字节的地址视为 4 字节对象的地址,因为可能存在对齐要求。
例如,在某些硬件平台中,在不是 4 的倍数的地址处访问 4 字节整数是段错误,而不仅仅是性能问题。
您在以下行中使用了 C 样式转换:return *(T*)(mData)
。C 型演员表
通过混合使用
static_cast
、const_cast
和reinterpret_cast
将一种类型转换为另一种类型
因此,由于const_cast
和static_cast
不能在不相关的类型之间强制转换,因此此行等同于:return *reinterpret_cast<T*>(mData)
这段代码访问一个reinterpret_cast
的结果,c++要求,给定DynamicType
byte
并且AliasedType
是T
,以下1必须为真:
AliasedType
(可能符合简历标准(DynamicType
AliasedType
和DynamicType
都是指向同一类型的
指针(可能是多级的,可能是每个级别的CV合格(AliasedType
是(可能符合 CV 条件的(signed
或unsigned
变体DynamicType
AliasedType
是一种聚合类型或union
类型,它将上述类型之一保存为元素或非静态成员(递归地包括子聚合的元素和所包含联合的非静态数据成员(:这使得获得指向struct
或union
的可用指针变得安全AliasedType
是DynamicType
的基类(可能符合 cv 条件(,DynamicType
是没有非静态数据成员的标准布局类,AliasedType
是其第一个基类AliasedType
是char
、unsigned char
或std::byte
:这允许检查任何对象的对象表示为字节数组
如果T
符合这些规范之一,那么您的代码无趣,无法从一种类型转换为另一种类型,但这是合法的。如果不是,则您的代码引入了未定义的行为,应被视为有害行为。