为什么不应该直接访问__m128i字段
Why should you not access the __m128i fields directly?
我在MSDN上读到这个,它说
不应直接访问__m128i字段。但是,可以在调试器中看到这些类型。类型为 __m128i 的变量映射到 XMM[0-7] 寄存器。
但是,它没有解释原因。这是为什么呢?例如,是以下"坏":
void func(unsigned short x, unsigned short y)
{
__m128i a;
a.m128i_i64[0] = x;
__m128i b;
b.m128i_i64[0] = y;
// Now do something with a and b ...
}
与其像上面的例子那样做赋值,不如使用某种load
函数吗?
字段m128i_i64
和family是编译器特定的扩展Microsoft。它们在大多数其他编译器中不存在。
尽管如此,它们对于测试目的还是有用的。
避免使用它们的真正原因是性能。硬件无法有效地访问 SIMD 矢量的各个元素。
- 没有允许您直接访问单个元素的说明。(SSE4.1 可以,但它需要一个编译时常量索引。
- 由于存储转发失败,通过内存可能会招致非常大的损失。
AVX 和 AVX2 不会扩展 SSE4.1 指令以允许访问 256 位矢量中的元素。据我所知,AVX512 不会用于 512 位矢量。
同样,集合内联(如_mm256_set_pd()
)也会遇到同样的问题。它们要么作为一系列数据改组操作实现。或者通过记忆并承担商店转发摊位。
这就引出了一个问题:是否有一种有效的方法可以从标量组件填充 SIMD 矢量?(或将 SIMD 矢量分离为标量分量)
简短回答:不是真的。使用 SIMD 时,您需要以矢量化形式完成大量工作。因此,初始化开销应该无关紧要。
相关文章:
- 将结构字段的类型展开为可变模板参数
- 将位字段导出到数组
- 为了方便起见,我应该避免公开私有字段变量吗
- 当字段可以为null时,如何使用C++接口在Avro中写入数据
- 在java中读取c++字节的位字段
- 链接器找不到在虚拟类 c++ 中访问的静态字段的符号
- 私有字段对象与私有继承?
- 声明没有默认构造函数的字段
- C++内存模型和位字段的最大序列
- 声明为无效的变量或字段'...' Ardunio 编译器上的错误
- 如何在QByteArray中放置和检索位字段而不会感到痛苦?
- C++ win32 如何使密码字段可选并启用复制和粘贴?
- 如何通过UDP接收QByteArray并将其解析为位字段结构?
- 仅匹配集合中的某些字段
- 结构字段名称与 GDB 中的 STL 数组冲突
- 如何使用位字段将数据从二进制文件复制到结构中?
- 结构体和类的不同大小(),彼此具有相同的字段类型
- 如何避免在数据结构中包含存储为字段的类?
- 聚合初始化和删除的复制构造函数,也称为不可复制的 obejcts 作为字段
- C++:用户定义的类,以成员字段作为地址