0

我有一个结构

struct Point
{
 int x;
 int y;
float val;
}

我打算使用这个结构来表示稀疏矩阵(我知道 CUSPARSE 和 CUSP,但我只是打算使用推力执行一些测试)并使用推力算法执行操作。

根据我在 CUDA 编程教程中研究的内容,始终建议使用数组结构而不是结构数组来更好地进行内存合并。

如果是这种情况,那么如果我使用上述结构在 device_vector 中存储非零(数百万级)怎么办,这个 device_vector 在处理推力算法时是否会在 GPU 内使用未对齐的内存访问?

我问这个是因为我可能需要访问这个 device_vector 内的不规则步幅并通过传递多个函数对象来执行算法操作。

它会像在数组结构上运行的自定义内核一样高效吗?

谢谢。

4

1 回答 1

4

假设合并的内存访问模式,NVIDIA CUDA 设备可以有效地访问 4、8 和 16 字节结构。为此,CUDA 标头定义了您可以使用的 structs int2int4float2、等。float4它们被定义为具有有效的对齐方式,因此我建议使用而不是您的自定义 Point 结构

typedef int2 Point;

当对这些小结构的数组的所有内存访问都是连续的(例如合并)时,每个结构元素中的所有数据都被读/写它的线程使用,那么这种类型的 AOS 访问是非常有效的。事实上,使用像这样的向量结构通常可以导致比标量数据访问更高的内存吞吐量,因为正在运行的内存事务增加。

Thrustzip_iterator专门提供对 SOA 数据进行操作的便利性和(编码)效率,就好像它是 AOS 数据一样。因此,虽然小结构在直接 CUDA C++ 中是有效的,但在使用 Thrust 时,您可以选择为每个结构成员使用单独的,并使用调用前和其他推力算法device_vector将它们压缩在一起。Thrust 示例代码中包含了这方面的示例。zip_iteratortransform

于 2012-07-02T06:42:55.230 回答