gpt4 book ai didi

c++ - CUDA 中的复数/cuComplex 算术

转载 作者:行者123 更新时间:2023-11-30 01:58:23 27 4
gpt4 key购买 nike

我是 CUDA 的新手,想了解更多关于复数运算及其速度影响的信息。

我需要为“j[]”数组中的所有元素求解以下复数方程并将答案存储在“Ans[]”中:

Ans [0] = (2.0/((20.5*(j[0]*j[0]))+(5.55*j[0])+20));
Ans [1] = (2.0/((20.5*(j[1]*j[1]))+(5.55*j[1])+20));
...
...
...
Ans [n] = (2.0/((20.5*(j[n]*j[n]))+(5.55*j[n])+20));

因为我需要对“j”的所有元素执行相同的计算,所以我可以并行化这段代码并让每个线程/ block 负责每个计算(blockIdx.x = 0 -> Ans [0] 等)据我了解,如果我对很多元素并行执行此操作,我应该能够看到速度的提高。然而,一行c++代码可以写的东西,在GPU中需要几行代码才能完成。

我的问题是,所有额外的代码行是否意味着更长的处理时间,因为它涉及在许多临时中保存中间值。如果是这样,当元素数量少于(比如说)1000 时,在 GPU 中进行此类计算是否仍然有意义? (任意数量)

等式:

C++ -> Ans [0] = (2.0/((20.5*(j[0]*j[0]))+(5.55*j[0])+20));

我的 GPU 版本:

int tid = blockIdx.x;

temp1[tid] = cuCmul(j[tid], j[tid]);
temp2[tid] = cuCmul(temp1[tid], make_cuDoubleComplex(20.5, 0));
temp3[tid] = cuCmul(j[tid], make_cuDoubleComplex(5.55, 0));
temp4[tid] = cuCadd(temp2[tid], temp3[tid]);
temp5[tid] = cuCadd(temp4[tid], make_cuDoubleComplex(20, 0));
Ans[tid] = cuCdiv(make_cuDoubleComplex(2.0, 0), temp5[tid]);

此外,如果有更有效的方式为 GPU 编写此代码,请告诉我

最佳答案

what can be written in one line of c++ code takes a few lines to do in the GPU.

这可能不是真的,至少对于您展示的示例而言是这样。您似乎担心临时存储,但编译器(主机和 GPU)非常擅长确定临时存储是否有意义,并对其进行优化。许多程序员陷入这样一种陷阱,即他们编写的 C 代码在存储使用和操作顺序方面很好地表示了机器将要执行的操作,但对于现代编译器而言,情况通常并非如此。

例如,您说这是您的 CPU 代码:

Ans [0] = (2.0/((20.5*(j[0]*j[0]))+(5.55*j[0])+20));

GPU 版本可以写成:

Ans [0] = cuCdiv(make_cuDoubleComplex(2.0, 0), cuCadd(cuCadd(cuCmul(cuCmul(j[tid], j[tid]), make_cuDoubleComplex(20.5, 0)), cuCmul(j[tid], make_cuDoubleComplex(5.55, 0))), make_cuDoubleComplex(20, 0)));

不使用显式临时存储。 (但是,代码肯定难以阅读。)但是在主机 (C) 或设备 (GPU) 情况下“幕后”发生的事情可能看起来不同。编译器通常比程序员更擅长计算如何优化这样的一行或几行代码。

首先让您的代码运行。然后对其进行基准测试(时间)。然后决定是否要仔细研究优化。 visual profiler 等工具可以帮助发现优化机会。

即使您的主机 C 代码看起来很简单,但请记住,复数仍然有 2 个与之关联的量。尽管这在(抽象的)C 代码中并不明显,但“在幕后”,编译器仍在执行必要的操作以分别处理数字以适合 +、-、*、/的各种操作

My question is, do all the additional lines of code mean longer processing time as it involves saving intermediate values in numerous temps.

不一定,因为我上面描述的原因。您对任一实现所做的工作基本相同,编译器将观察到这一点并可能生成类似的机器代码。

If so, would it still make sense to do this sort of calculation in the GPU when the number of elements are less than, say, 1000? (arbitrary number)

如果您像这样计算的答案总数约为 1000,那么对于现代 GPU 而言,您的问题“相当小”。现代 GPU 可能有 8 个(或更多)SM,每个 SM 能够同时运行 1 到 3 个 warp(32 个线程),并且机器还需要相当稳定的“准备运行”的 warp,以保持所有管道(内存、计算等)忙。 1000 个线程可能是实现 GPU 合理利用的最低限度。显然,这在很大程度上取决于您将在哪个或哪些 GPU 上运行。例如,笔记本电脑中的小型低端 GPU 可能能够以更小的问题实现高利用率。但是,如果您的计算范围是您在此处显示的类型的 1000,我也无法想象它会在 CPU(主机代码)上花费很多时间。

关于c++ - CUDA 中的复数/cuComplex 算术,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17532202/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com