查询特定变量的对齐方式
Query the alignment of a specific variable
C++11引入了alignas
说明符来指定变量的对齐方式,并引入了alignof
运算符来查询类型的默认对齐方式。然而,我看不出有任何方法可以使特定变量对齐。让我们举以下琐碎的例子:
alignas(16) float* array;
以下是我们可以做的:
alignof(float*)
返回8,这显然不是我们想要的alignof(array)
返回16,这正是我们想要的,但这是一个编译器扩展;标准中指定的alignof
不能用于特定变量alignof(decltype(array))
返回8,这是意料之中的,但不是我们想要的std::alignment_of
是在alignof
的基础上实现的,所以它没有多大帮助
我想要一种机制来确认特定变量array
在16字节边界上对齐。标准中是否有执行此类查询的内容?
您可以尝试使用以下内容:
bool is_aligned(const volatile void *p, std::size_t n)
{
return reinterpret_cast<std::uintptr_t>(p) % n == 0;
}
assert(is_aligned(array, 16));
以上假设了平坦的地址空间,并且CCD_ 10上的算术等同于CCD_ 11上的算术。
虽然这些条件适用于大多数现代平台,但这两种条件都不是标准所要求的。
当将void *
强制转换为uintptr_t
时,实现完全可以执行任何转换,只要从uintptr_t
强制转换回void *
时可以反转转换即可(请参阅什么是uintptr_t数据类型)。
N4201中的进一步细节(除其他外,它提出了is_aligned()
操作)。
编辑
这里需要
volatile
吗?
它允许类似以下内容:
alignas(16) volatile float a;
assert(is_aligned(&a, 16));
如果没有volatile
,您会得到错误
第一个参数没有从"volatile float*"到"const void*"的已知转换
进一步参考:
- 为什么以及何时被强制转换为char volatile&需要吗
- 为什么一个指向易失性指针的指针,比如";volatile int*p";,有用吗
这目前由EWG 98处理。我提交了一篇关于的论文
alignas
说明符适用于对象,影响它们的对齐要求,但不影响它们的类型。因此,目前无法确定对象的实际对齐要求。本文提出允许alignof
应用于对象和引用。
在这个时间点上,你能做的最好的事情就是定义一个单独的变量来保持变量的对齐。
你可以试试这个:
template<size_t size, typename T>
constexpr bool IsAlignedAs(const T& v)
{
return (reinterpret_cast<const size_t>(&v) % size) == 0;
}
std::cout << IsAlignedAs<16>(array) << std::endl;
std::cout << IsAlignedAs<32>(array) << std::endl;
相关文章:
- 为什么我可以将变量存储在不是其最小对齐方式的倍数的地址?
- 具有调整对齐方式的类型定义
- size_t的大小和对齐方式是否与ptrdiff_t相同?
- 逗号运算符在对齐方式中
- vcpkg:指定结构成员对齐方式
- 使用字节数组具有单字节对齐方式的结构是否安全
- C++对齐方式(何时使用对齐方式)
- 编译器会秘密增加结构的对齐方式吗?
- C++17 中函数参数的指针对齐方式
- 未在此范围内声明的对齐方式?
- 如何控制 clang 格式新行中 lessless 的对齐方式
- C++ 编译器正在更改我的结构的对齐方式.我怎样才能防止这种情况
- 是否有符合标准的方法来确定非静态杆件的对齐方式?
- 重载运算符是具有较小默认对齐方式的新增运算符
- 结构和对齐方式的大小
- Sizeof 舍入到对齐方式,但编译器仍将对象放在剩余的字节中
- 是否可以让 std::vector<char> 使用选定的内存对齐方式分配内存
- 对齐方式与指针中尾随零的数量有何关系
- 对齐方式究竟如何影响内存布局和新放置的巴哈维?
- 幻影类型是否与原始类型具有相同的对齐方式