上周尝试用opencl求极大值,在网上查到大多是求和,所谓的reduction算法。不过思路是一样的。

CPP:

   int err = ;
unsigned long int nNumCount = ;
int nLocalSize = ;
int nGroupSize = ;
int nGroup = nGroupSize / nLocalSize; int* pArray = new int[nNumCount];
unsigned long int nReal = ;
int nStart = GetTickCount();
for (int i=;i<nNumCount;++i)
{
pArray[i] = i*;
nReal += pArray[i];
}
cout<<GetTickCount() - nStart<<endl; cl_mem clmemArray = clCreateBuffer(context,CL_MEM_READ_WRITE,sizeof(int) * nNumCount,NULL,NULL);
err = clEnqueueWriteBuffer(queue,clmemArray,CL_TRUE,,sizeof(int)*nNumCount,pArray,,,);
cl_mem clmemRes = clCreateBuffer(context,CL_MEM_READ_WRITE,sizeof(int) * nGroup,NULL,NULL); nStart = GetTickCount(); err = clSetKernelArg(m_KerCalcRay,,sizeof(cl_mem),&clmemArray);
err = clSetKernelArg(m_KerCalcRay,,sizeof(cl_mem),&clmemRes);
err = clSetKernelArg(m_KerCalcRay,,sizeof(int)*nLocalSize,);
err = clSetKernelArg(m_KerCalcRay,,sizeof(int),&nNumCount); size_t localws[] = {nLocalSize};
size_t globalws[] = {nGroupSize}; err = clEnqueueNDRangeKernel(queue,m_KerCalcRay,,NULL,globalws,localws,,NULL,NULL);
clFinish(queue); int* pRes = new int[nGroup];
err = clEnqueueReadBuffer(queue,clmemRes,CL_TRUE,,sizeof(int)*nGroup,pRes,,,);
clFinish(queue); unsigned long int nRes = ;
for(int i=;i<nGroup;++i)
{
nRes += pRes[i];
}
  assert(nRes == nReal);

kernel:

__kernel void ReduceSum(__global int* num,__global int* res,__local int* pData,int nCount)
{
unsigned int tid = get_local_id();
unsigned int bid = get_group_id();
unsigned int gid = get_global_id();
unsigned int localSize = get_local_size();
unsigned int globalSize = get_global_size(); int nRes = ;
while(gid < nCount)
{
nRes += num[gid];
gid += globalSize;
}
pData[tid] = nRes;
barrier(CLK_LOCAL_MEM_FENCE); // do reduction in shared mem
for(unsigned int s = localSize >> ; s > ; s >>= )
{
if(tid < s)
{
pData[tid] += pData[tid + s];
}
barrier(CLK_LOCAL_MEM_FENCE);
} if(tid == )
res[bid] = pData[]; }

Reduction求和是这样一种方法,比如8个数0到7依次存放,求和的时候就是下标0和4、1和5、2和6、3和7,求和结果放到下标0、1、2、3中(同步一把barrier(CLK_LOCAL_MEM_FENCE))。然后继续就是0和2,、1和3求和结果放到0、1中。如此往复、最终结果就放到下标0中啦。

另:我试过循环展开减少同步次数、不过效率增长微乎其微。

Opencl 并行求和的更多相关文章

  1. 【MPI】并行求和

    比较简单的并行求和 读入还是串行的 而且无法处理线程数无法整除数据总长度的情况 主要用到了MPI_Bcast MPI_Scatter MPI_Reduce typedef long long __in ...

  2. Python的并行求和例子

    先上一个例子,这段代码是为了评估一个预测模型写的,详细评价说明在 https://www.kaggle.com/c/how-much-did-it-rain/details/evaluation, 它 ...

  3. OpenMP共享内存并行编程详解

    实验平台:win7, VS2010 1. 介绍 平行计算机可以简单分为共享内存和分布式内存,共享内存就是多个核心共享一个内存,目前的PC就是这类(不管是只有一个多核CPU还是可以插多个CPU,它们都有 ...

  4. 《OpenCL异构计算》新版中译本派送中!

    <OpenCL异构计算1.2>新鲜出炉,目前市面上仍一书难求!我们已向清华出版社订购到第一批新书.关注异构开发社区,积极参与,就有可能免费获取新书! 1.如果您异构社区的老朋友,请关注:1 ...

  5. OpenCL Workshop 1 —— 数字音频滤波

    Introduction 这两年深度学习大火,Cuda跟着吃红利,OpenCL发展也很快.虽然OpenCL不是事实上的标准,但是作为开放标准,适应性是很强的,除了显卡之外,CPU/FPGA上都可以执行 ...

  6. Java8的新特性--并行流与串行流

    目录 写在前面 Fork/Join框架 Fork/Join框架与传统线程池的区别 传统的线程池 Fork/Join框架 Fork/Join框架的使用 Java8中的并行流 写在前面 我们都知道,在开发 ...

  7. 给深度学习入门者的Python快速教程 - 番外篇之Python-OpenCV

    这次博客园的排版彻底残了..高清版请移步: https://zhuanlan.zhihu.com/p/24425116 本篇是前面两篇教程: 给深度学习入门者的Python快速教程 - 基础篇 给深度 ...

  8. Hadoop与Spark比较

    先看这篇文章:http://www.huochai.mobi/p/d/3967708/?share_tid=86bc0ba46c64&fmid=0 直接比较Hadoop和Spark有难度,因为 ...

  9. 【java并发系列】Fork/Join任务(转)

    原文链接 当我们需要执行大量的小任务时,有经验的Java开发人员都会采用线程池来高效执行这些小任务.然而,有一种任务,例如,对超过1000万个元素的数组进行排序,这种任务本身可以并发执行,但如何拆解成 ...

随机推荐

  1. Maven私有仓库搭建和使用

    下载和安装 下载地址: http://www.sonatype.com/nexus-repository-oss 安装: Linux版的无需安装,直接解压即可,然后进入bin目录下,运行./nexus ...

  2. shell程序设计

    1.shell脚本的基本概念: (1)Shell执行的是称为shell程序,这些程序通常被称为脚本. (2)Shell是一个用户和系统间接口的程序,它允许用户向操作系统输入需要执行的命令. (3)sh ...

  3. Java生成与解析二维码

    1.下载支持二维码的jar包qrcode.jar和qrcode_swetake.jar, 其中qrcode_swetake.jar用于生成二维码,rcode.jar用于解析二维码,jar包下载地址(免 ...

  4. PHP常用函数总结(不定期更新)

    array_merge函数和两个数组相加的区别 array_merge函数,在出现相同的索引数组,会把两个数组中的索引数组,进行融合,以第一个数组的索引最大值往后相加,如果是关联数组,后面数组的值覆盖 ...

  5. Excel小写金额转大写金额公式

    =IF(ROUND(A6,2)<0,"无效数值",IF(ROUND(A6,2)=0,"零",IF(ROUND(A6,2)<1,"" ...

  6. 提交到github远程仓库遇到的问题

    1.could not read from remote repository 可能原因是没有将ssh 密匙添加到github,所以没有权限 解决办法: 1. ssh-keygen -C 'your@ ...

  7. 尚学堂Spring视频教程(四):使用Annotation

    之前我们的bean都配置在XML里,并且通过bean的property标签来指定依赖关系,如果项目很大,那岂不是要配置很多这样的property标签?Spring提供了注解的方式来解决这个问题 @Au ...

  8. windows下sass安装 以及一些要注意的问题

    都说sass 环境难配其时也没那么难 按照以下步骤一下一下来还是挺快的 如果你是喜欢less 那就当我没说 233333 1.sass 是基于ruby这门语言的需要使用 rubygem这个包管理器安装 ...

  9. LR12.53—第3课:重播Vuser脚本

    第3课:重播Vuser脚本 在前面的教训,你记录了一组典型的用户行为,并准备重播脚本. 重播脚本之前,您可以配置脚本的运行时设置,它定义了Vuser的行为. 注:记录与基于Web的协议的地方WebTo ...

  10. C++学习基础十二——纯虚函数与抽象类

    一.C++中纯虚函数与抽象类: 1.含有一个或多个纯虚函数的类成为抽象类,注意此处是纯虚函数,而不是虚函数. 2.如果一个子类继承抽象类,则必须实现父类中的纯虚函数,否则该类也为抽象类. 3.如果一个 ...