求助:关于opencl中CPU和GPU对double的计算问题

cxjchen 2014-08-11 05:33:29
处理器:AMD APU with Radeon(TM) R7 Graphics
计算两个数组的卷积
int main(int argc, char* argv[])
{
unsigned int NUM=256*256;
double* d_a = new double[NUM*sizeof(double)];
double* d_b = new double[NUM*sizeof(double)];
for(int i=0;i<NUM;i++){
d_a[i]=2.3+(double)i;
d_b[i]=1.9+(double)i;
}
double result=convolution(d_a,d_b,NUM);
printf("%f",result);
getchar();
return 0;
}


在CPU运行时结果是93831864344248.344000
在GPU运行时结果是93831864344248.312000
哪位高手能大概解释下是什么原因吗,求助求助!!
...全文
536 5 打赏 收藏 转发到动态 举报
写回复
用AI写文章
5 条回复
切换为时间正序
请发表友善的回复…
发表回复
cxjchen 2014-08-14
  • 打赏
  • 举报
回复
这是CPU的info
cxjchen 2014-08-14
  • 打赏
  • 举报
回复
当用float定义的时候没有任何问题,如果用double定义,数值较小也没问题,当数值调大,比如256*256个(double)102546456*204864654的和,CPU和GPU就会有一点误差,我是win8.1,用的vs2012,AMD的APU,请问是x87编译器的问题吗,怎么看CPU编译时用的什么编译器呀???
cxjchen 2014-08-14
  • 打赏
  • 举报
回复
还有就是,比如我令double a=3.3,b=7.7,一共求256*256次乘积和,在cpu上和gpu上结果会有一点误差,但如果求256次乘积和,计算机结果就是一样的,如果用float定义,结果都一样,到底是怎么回事,希望有人能够给个确切一点的回答,感激不尽!!!
fronteer 2014-08-13
  • 打赏
  • 举报
回复
你的 convolution() 是库函数还是头文件中定义的和宏? 我认为这个结果和 CPU 上编译 onvolution() 代码的环境有关. 解释如下: 1) 我们在编译 GPU kernel 代码时通常是不给 runtime 编译器 提供任何编译选项的。 Double 类型的实现在 GPU 上是标准的 IEEE 754 的双精度类型, 其精度是 64bit 2) 在 CPU 上, C 的 Double 类型的实现则和编译关系太大了. 在现在的 x86-64 机器上可以做浮点运算的设备(或方式)有两个,一个是 x87 浮点寄存器及指令集, 另外一个是 SSE寄存器及相关浮点指令集。前者实现的Double是对IEEE 754双精度类型的扩展, 精度达 80位, 后者精度是 64 位. 所以如果你的CPU代码编译时用的是 x87, 则会可能会出现你说的结果差别. 3) 以Linux 上 Gcc 位例, 32位代码保留用 x87 做 double 类型计算, 64位代码保留用SSE指令做浮点计算。 但用户可以通过 gcc 的 -mfpmath 选项指定用于浮点计算的设备. 4) 另外,CPU 编译器的更具体达选项,比如规定舍入规则的选项,也能影响你的测试结果,如 gcc 的 fp-rounding-mode, rounding-math 选项的使用, 能改变浮点运算的舍入规则,从而影响你的测试结果
lcwyylcwyy 2014-08-12
  • 打赏
  • 举报
回复
1,GPU中的double并不是很精确,2,,要防止比较大的数加上比较小的数,这样会吃掉小数,或者两个相近的数相减,降低其有效位。

601

社区成员

发帖
与我相关
我的任务
社区描述
异构开发技术
社区管理员
  • OpenCL和异构编程社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧