为什么要使用:
kernel<<<512, 512>>>( ); //somewhere
__device__ void kernel( ) {
Code( );
}
而不是:
kernel<<<1, 512>>>( 512 ); //somewhere
__device__ void kernel( int n ) {
for ( int i = 0 ; i < n ; ++i ) {
Code( );
}
}
注意:我还没有CUDA GPU来检查它。
第一个以某种方式更快吗? GPU内核无法处理长时间运行的线程,或者在运行更长时间时失去速度?
我猜第二个(for-loop)在所需迭代次数与线程数不对齐时更好。 (我们可以更改最后一个线程\ core中的n
变量)
答案 0 :(得分:2)
CUDA的想法是你应该并行完成并行工作。整个执行架构旨在实现这一目标。任何真正 parallel 的东西,即逻辑的所有并行部分以锁步方式执行完全相同的逻辑,最好通过在多个核心上同时执行相同的指令,而不是执行许多指令在一个核心上进行复杂的分支和循环。
我建议你阅读Nvidia发布的关于CUDA的大量文档,特别注意warp,库冲突,本地内存,分支等。对GPU的编程并不简单,就像任何类型的并发编程一样,你应该期待这个过程是痛苦和昂贵的,除非你有一个非常好的理由是并发,并且很好地理解了很多低级细节。
答案 1 :(得分:0)
这是因为线程如何分配给GPU执行资源。 整个块在GPU上的流式多处理器之间分配。如果您使用单个块启动了网格,则内核将在一个SM上运行。这对于像Tegra K1这样的单个SM的小型GPU来说会很好,但是对于大多数具有多个SM的GPU(比如GTX Titan X上的24个),你会浪费大量的资源。 / p>