▶ OpenACC 的原子操作,用到了 C++ 的一个高精度计时器

● 代码,直接的原子操作

 #include <iostream>
#include <cstdlib>
#include <chrono> #define ATOMIC using namespace std;
using namespace std::chrono; int main()
{
high_resolution_clock::time_point t1 = high_resolution_clock::now();// 高精度计时器 const int count = ;
int sum = ; #pragma acc parallel loop copyout(sum)
for (int i = ; i < count; i++)
{
#ifdef ATOMIC
#pragma acc atomic update
#endif
sum++;
} high_resolution_clock::time_point t2 = high_resolution_clock::now();
duration<double> time = duration_cast<duration<double>>(t2 - t1); cout << "\nCount = " << count << ", duraion = " << time.count() << " s" << endl;
return ;
}

● 输出结果,不知道为什么,win10中的 pgCC 不能用

D:\Code\OpenACC\OpenACCProject\OpenACCProject>pgCC -acc -o acc_win10.exe main.cpp -Minfo
pgCC-Warning-C++ compilation is not supported: main.cpp

● 输出结果,WSL 中

// 不使用 OpenACC
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ pgc++ -std=c++ -o acc.exe main.cpp -Minfo
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ ./acc.exe Count = , duraion = 0.483907 s // 使用宏 ATOMIC,即使用原子操作
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ pgc++ -acc -std=c++ -o acc.exe main.cpp -Minfo
main:
, Generating copyout(sum)
Accelerator kernel generated
Generating Tesla code
, #pragma acc loop gang, vector(128) /* blockIdx.x threadIdx.x */
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ ./acc.exe Count = , duraion = 0.248377 s // 不用宏 ATOMIC,即不用原子操作
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ pgc++ -acc -std=c++ -o acc.exe main.cpp -Minfo
main:
, Generating copyout(sum)
Accelerator kernel generated
Generating Tesla code
, #pragma acc loop seq
, Accelerator restriction: induction variable live-out from loop: sum // 编译器提示强制原子操作
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ ./acc.exe Count = , duraion = 0.247399 s

● 优化一下,使用分段计数

 #include <iostream>
#include <cstdlib>
#include <chrono> using namespace std;
using namespace std::chrono; int main()
{
high_resolution_clock::time_point t1 = high_resolution_clock::now(); const int count = , length = count / ;// 每一段的长度
int sum = ; #pragma acc parallel loop copyout(sum)
for (int start = ; start < count; start+=length) // start 取每段的起点,共 count / length 段
{
const int end = (start + length < count) ? start + length : count; // 每段的终点
int subSum = ;
#pragma acc loop worker reduction(+:subSum)
for (int j = start; j < end; j++) // 每段从 start 加到 end
subSum ++; #pragma acc atomic update
sum += subSum; // 规约结果加到 sum 中来
} high_resolution_clock::time_point t2 = high_resolution_clock::now();
duration<double> time = duration_cast<duration<double>>(t2 - t1); cout << "\nCount = " << sum << ", duraion = " << time.count() << " s" << endl;
return ;
}

● 输出结果,好像好一点点

cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ pgc++ -acc -std=c++ -o acc.exe main.cpp -Minfo
main:
, Generating copyout(sum)
Accelerator kernel generated
Generating Tesla code
, #pragma acc loop gang /* blockIdx.x */
, #pragma acc loop seq /* threadIdx.y */
Generating reduction(+:subSum)
, Loop is parallelizable
cuan@CUAN:/mnt/d/Code/OpenACC/OpenACCProject/OpenACCProject$ ./acc.exe Count = , duraion = 0.246488 s

OpenACC 简单的原子操作的更多相关文章

  1. OpenACC 简单的直方图

    ▶ 简单的直方图,强调原子操作的使用 ● 代码 #include <stdio.h> #include <stdlib.h> #include <openacc.h> ...

  2. 对 cloudwu 简单的 cstring 进行简单解析

    题外话 以前也用C写过字符串,主要应用的领域是,大字符串,文件读取方面.写的很粗暴,用的凑合着.那时候看见云风前辈的一个开源的 cstring 串. 当时简单观摩了一下,觉得挺好的.也没细看.过了较长 ...

  3. zookeeper源码分析之一服务端启动过程

    zookeeper简介 zookeeper是为分布式应用提供分布式协作服务的开源软件.它提供了一组简单的原子操作,分布式应用可以基于这些原子操作来实现更高层次的同步服务,配置维护,组管理和命名.zoo ...

  4. 第二章 管理程序流(In .net4.5) 之 管理多线程

    1. 概述 本章包括同步资源以及取消长时间任务相关的内容. 2. 主要内容 2.1 同步资源 ① lock关键字实现.会阻塞程序,有可能会导致死锁. ② volatile关键字可以禁用编译优化,用于避 ...

  5. C 实现一个跨平台的定时器 论述

    引言 今天我们要讲述和构建的是一个跨平台多线程C的定时器对象,粒度是毫秒级别.可以称之为简易的timer, sctimer.h 库. 首先看总的接口,看门见客. sctimer.h #ifndef _ ...

  6. 对云风 cstring 第二次解析

    前言 从明天起 关心粮食和蔬菜 我有一所房子 面朝大海 春暖花开 本文前提条件 1.了解 posix 线程 2.了解 原子操作 3.具备简单C基础,或者 你也敲一遍. 如果上面不太清楚,你可以翻看我以 ...

  7. 论文笔记(8):BING: Binarized Normed Gradients for Objectness Estimation at 300fps

    译文: <基于二值化赋范梯度特征的一般对象估计> 摘要: 通过训练通用的对象估计方法来产生一组候选对象窗口,能够加速传统的滑动窗口对象检测方法.我们观察到一般对象都会有定义完好的封闭轮廓, ...

  8. java基础系列--volatile关键字

    原创作品,可以转载,但是请标注出处地址:http://www.cnblogs.com/V1haoge/p/7833881.html 1.volatile简述 据说,volatile是java语言中最轻 ...

  9. Linux内核同步

    Linux内核剖析 之 内核同步 主要内容 1.内核请求何时以交错(interleave)的方式执行以及交错程度如何. 2.内核所实现的基本同步机制. 3.通常情况下如何使用内核提供的同步机制. 内核 ...

随机推荐

  1. WinForm 实现点击一个按钮,执行另一个按钮事件

    C# 代码如下: private void button1_Click(object sender, EventArgs e) { this.button1.Click += new System.E ...

  2. (2)字符编码关系和转换(bytes类型)

    ASCII 占一个字节,只支持英文 GB2312 占2个字节,只支持6700+汉字 GBK 是GB2312的升级版,支持21000+汉字 Shift-JIS 日本字符编码 ks_c-5601-1987 ...

  3. cache、session与cookie

    cache.session.cookie的区别 session把数据保存在服务器端,每一个用户都有属于自己的Session,与别人的不冲突 就是说,你登陆系统后,你的信息(如账号.密码等)就会被保存在 ...

  4. Linux设备树

    一.设备树编译 1.编译设备树:cd linux-x.xx & make dtbs,生成的dtb在目录linux-x.xx/arch/xxx/boot/dts下 2.反编译dtb,生成dts: ...

  5. vulcanjs 核心架构概念

    基于包的架构 为了保证系统的灵活以及可扩展,vulcanjs 使用基于包的架构设计,每一个功能都是一个包,可以方便的添加,移除 扩展.而不是修改 vulcan 的设计哲学是进行系统扩展,而不是编辑修改 ...

  6. 万年历(hao123)代码

    网上有很多类似的代码,比如网站:hao123,IP138.日梭万年历网络版 等等,不过日梭万年历相对比较详细,也可以看看另外一篇文章的介绍: 日梭万年历网络版:http://www.cnblogs.c ...

  7. mysql 事务隔离级别详解

    事物的 隔离级别,说简单非常简单(新手也能说出 是个隔离级别 和 影响),说男也非常难.(很多 有几年编程 经验的程序员依旧搞不清楚) 废话不多少 直接开始: 事务的隔离级别 是用来描述 事务的读关系 ...

  8. Keepalived stable tarball

    Keepalived stable tarball Keepalived for Linux - Version 1.3.5 - March 19, 2017 Keepalived for Linux ...

  9. Linux内核编译:很少有人提及的一些内容

    1. 你可以使用O=参数将编译结果放到其他位置(非源代码目录),例如:make O=~/build ... 这样做的好处是你的源代码目录不会受到任何改变:你甚至可以在不同的体系结构间共享源代码. 注意 ...

  10. java操作Excel之POI(1)

    一.新建工作簿.sheet.单元格 public static void main(String[] args) throws Exception { Workbook wb = new HSSFWo ...