blender找不到GPU怎么解决?

打算通过OpenCV的GPU模块优化现有代码的运行效率,怀抱着美好愿望开始了代码的改写工作。改写的过程并不顺利,遇到了不少问题。例如,gpu模块提供的接口非常坑爹,相当一部分不支持浮点类型(像histogram、integral这类常用的都不支持);又如,遇到阈值判断的地方,就必须传回cpu处理,因为gpu函数都是并行处理的,每改写完一个算法模块,就测试一下运行效率,有的时候是振奋人心,有的时候则是当头棒喝——比CPU还慢?

经过一系列的google,终于找到原因:



整段代码的第一条与GpuMa有关的语句就是所谓的first gpu function,这里CUDA需要初始化设备上下文,而该操作是非常耗费时间的!

在代码开头,或者类的构造函数,加入:

src1随便赋一个初值,关键是调用一次涉及GpuMat的操作(其它gpu函数也行),那么段代码就实现了CUDA的初始化。

经过实测,这里需要耗费400ms!尽管是像上面那么简单的两个语句,只要是整段代码的第一次调用gpu相关操作,默认执行CUDA的初始化!在其它机器上不一定是400ms,应该跟具体的PC硬件有关。

往后的gpu的操作都不会那么慢,但一旦涉及upload、download(显存与内存的数据传递),时间成本都达到ms级别!

总结一句,GPU的并行处理的确很快,但数据传入GPU的开销实在太大,往往影响了代码的整体效率。

现在的项目是,C++写的算法,做成dll供C#调用;理所当然的,gpu的操作都放在C++的接口I函数里;那问题就来了,每次C#调用C++的函数,都要执行CUDA的初始化,都要耗费400ms在无意义的操作上,对于算法的实时性要求简直不能忍受!除非,在C#里面先初始化CUDA,但这样可行吗?又合理吗?

现在总算搞明白,为什么网上没多少opencv gpu的资源,用的人不多嘛,实在坑爹啊!这么大的弊端,真的用过就怕了,害我浪费了那么多时间去优化,算法主体部分是快了不少,原本200ms,现在到了100ms的水平,但就这坑爹的CUDA初始化400ms就够抵消所有的成果!

以后在引入gpu之前,真的要好好审视本算法的当前运行效率,只有当前运行时间远大于CUDA初始化的耗时,才有引入的必要!的确,我是没有做好运算量的评估,现在的算法的运算量根本用不到gpu!

问题1、CUDA初始化设备上下文非常耗时。

可以通过在程序开头进行任意一项与CUDA相关的操作,如定义一个GpuMat:

第一条CUDA语句将会非常耗时,但之后都会恢复正常。

问题2、访存时间(latency)影响程序的整体效率。

两个途径:减少数据在CPU和GPU之间的传递次数;运算量非常小的部分不要用GPU,数据量非常大、循环次数非常多的时候才使用GPU。

前者是最直接的手段,后者则是GPU的使用原则,可见以下例子:

分别用CPU和GPU实现高斯滤波

以上是GPU的代码,锁页能够加速数据在CPU和GPU之间的传递

运行结果:只计算高斯滤波函数的耗时,GPU是CPU的1/3~1/2,然而考虑上访存时间,GPU甚至比CPU还慢!

但如果进行10次高斯滤波,GPU的优势就能够得以体现:

以上是进行10次滤波的GPU代码,同时,CPU代码也执行10次滤波

运行结果:算上方寸时间,GPU的总耗时是CPU的1/5,如果执行100次滤波,则为1/10

但需要注意的是,运算量不仅跟执行次数有关,还跟数据量有关。按道理说,GPU对数据量越大的情况越有利,但在opencv的CUDA模块中,矩阵较大的数据(行列数较多)将大大增加数据传递的耗时,因为GpuMat本身对矩阵大小是有限制的,所以这又制约了CUDA并行的效率,除非使用CUDA编程合理分配数据和线程,opencv本身对大矩阵是无能为力的。

以下博文是更深层次的讨论CUDA代码优化:

执行单线程的做法,无疑会闲置非常多的并行计算资源,我们必须采用多线程,这样效率就会得到大幅度的提升。在GPU编程中,有一个叫“掩藏”(Hide)的概念。它的意思是指线程因为访问存储器或者阻塞等其它原因造成的延迟,但由于分配的线程足够多,导致整体上看GPU仍然处于忙碌的状态。

建议先跟着b站教程【up主:刘二哥的二已被注册、VFXinfo官方账号、只剩一瓶辣椒酱等】走一遍。如果你是想问为什么你的模型没有颜色,因为你没有做模型的材质,没有布光;如果你是想问摄像机视角为什么这么怪,按CTRL不放,再按键盘右侧的0进入摄像机视角,然后按T在视图里勾选锁定摄像机视角,之后你就可以调整视角了,调整好之后把刚才点的勾去掉,鼠标中键按住拖一下鼠标回到世界环境。

我要回帖

更多关于 blender物体坐标轴看不到了 的文章

 

随机推荐