基于OpenCL的mean filter性能

1.對于一個標準的3*3 均值濾波,kernel代碼如下:

使用buffer/image緩沖對象

__kernel void filter(__global uchar4* inputImage, __global uchar4* outputImage, uint N)
{int x = get_global_id(0);int y = get_global_id(1);int width = get_global_size(0);int height = get_global_size(1);int k = (N-1)/2;int n = N*N; //n*nif(x < k || y < k || x > width - k - 1 || y > height - k - 1)
{ 
outputImage[x + y * width] = inputImage[x + y * width];return;
}uint4 finalcolor = (uint4)(0);int i,j;for(j = y - k; j <= y + k; j++)
{for(i = x - k; i <= x + k; i++)
{
finalcolor = finalcolor + convert_uint4(inputImage[i + j * width]);
}
} outputImage[x + y * width] = convert_uchar4(finalcolor/n);}

__kernel void filterImg( image2d_t inputImage, __write_only image2d_t outputImage, uint N)
{int x = get_global_id(0);int y = get_global_id(1);int width = get_global_size(0);int height = get_global_size(1);uint4 temp = read_imageui(inputImage, imageSampler, (int2)(x,y));int k = (N-1)/2;int n = N*N; //n*nif(x < k || y < k || x > width - k - 1 || y > height - k - 1)
{
write_imageui(outputImage, (int2)(x,y), temp);return;
}/* k*k area */
uint4 finalcolor = (uint4)(0);int i,j;for(j = y - k; j <= y + k; j++)
{for(i = x - k; i <= x + k; i++)
{
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(i,j));
}
}finalcolor = finalcolor/n;write_imageui(outputImage, (int2)(x,y), finalcolor);}

對一個2048*2048的圖像執行filter操作,

image

image

?

image

image

global work size = {2048, 2048, 1}, group work size = {16, 16}, 一般group work size應該為64的倍數,因為對于AMD顯卡,wave是基本的硬件線程調度單位。

使用了6個GPRs,沒有使用ScratchRegs,ScratchRregs是指用vedio meory來模擬GPR,但是線程執行的速度會大大降低,應盡量減少ScratchRegs的數量。

可以看到,使用image對象kernel執行時間要短,但奇怪的是各項性能參數都是buffer對象領先,除了alu busy和alu指令數目。

改為下面的kernel代碼,性能會有所提高

?

__kernel void filter(__global uchar4* inputImage, __global uchar4* outputImage, uint N)
{int x = get_global_id(0);int y = get_global_id(1);int width = get_global_size(0);int height = get_global_size(1);if(x < 1 || y < 1 || x > width - 2 || y > height - 2)
{ 
outputImage[x + y * width] = inputImage[x + y * width];return;
}uint4 finalcolor = (uint4)(0);finalcolor = finalcolor + convert_uint4(inputImage[x-1+( y-1) * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+( y-1) * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+1+( y-1) * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x-1+y * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+y * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+1+y * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x-1+( y+1) * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+( y+1) * width]);
finalcolor = finalcolor + convert_uint4(inputImage[x+1+( y+1) * width]);outputImage[x + y * width] = convert_uchar4(finalcolor/9);}
__kernel void filter1(__global uchar4* inputImage, __global uchar4* outputImage, uint N)
{int x = get_global_id(0);int y = get_global_id(1);int width = get_global_size(0);int height = get_global_size(1);int k = (N-1)/2;int n = N*N; //n*nif(x < k || y < k || x > width - k - 1 || y > height - k - 1)
{ 
outputImage[x + y * width inputImage[x + y * width];return;
}// if(x==209 && y ==243)//{// printf("final color:%d,%d,%d,%d\n", finalcolor.x, finalcolor.y, finalcolor.z,finalcolor.w);// }uint4 finalcolor = (uint4)(0);int i,j;for(j = y - k; j <= y + k; j++)
{for(i = x - k; i <= x + k; i++)
{
finalcolor = finalcolor + convert_uint4(inputImage[i + j * width]);
}
} outputImage[x + y * width] = convert_uchar4(finalcolor/n);}
__kernel void filterImg( image2d_t inputImage, __write_only image2d_t outputImage, uint N)
{int x = get_global_id(0);int y = get_global_id(1);int width = get_global_size(0);int height = get_global_size(1);uint4 temp = read_imageui(inputImage, imageSampler, (int2)(x,y));if(x < 1 || y < 1 || x > width - 2 || y > height - 2)
{
write_imageui(outputImage, (int2)(x,y), temp);return;
}/* k*k area */
uint4 finalcolor = (uint4)(0);finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x-1,y-1));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x,y-1));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x+1,y-1));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x-1,y));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x,y));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x+1,y));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x-1,y+1));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x,y+1));
finalcolor = finalcolor + read_imageui(inputImage, imageSampler, (int2)(x+1,y+1));finalcolor = finalcolor/9;write_imageui(outputImage, (int2)(x,y), finalcolor);}

image

image

image

image

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/448820.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/448820.shtml
英文地址,請注明出處:http://en.pswp.cn/news/448820.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Docker 實戰:編寫 Dockerfile

一、編譯鏡像 前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 1. 編譯鏡像 Dockerfile類似于Makfile&#xff0c;用戶使用docker build就可以編譯鏡像&#xff0c;使用該命令可以設置編譯…

dubbo-環境搭建,實現一個簡單地dubbo實例(附github地址)

一、建立maven模塊和provider、consumer、service子模塊&#xff0c;其中service是開發接口的模塊 建立一個maven模塊&#xff0c;不選擇樣板&#xff0c;直接next知道完成&#xff0c;建立三個子模塊,建立完后發現各個模塊的java目錄不是源目錄 右鍵——>make Directory as…

static 二次理解

當api底層用到static修飾的話&#xff0c;因為是類的&#xff0c;此容器中只有一份轉載于:https://blog.51cto.com/jiaxiaoxu/2394844

AMD 5XXX 系列顯卡的 peak bandwidth計算

在ATI Stream Computing Programming Guide中&#xff0c;例舉了AMD 5系列顯卡的參數信息。 我比較關注其中Peak bandwidths的計算&#xff0c;以便在opencl程序測試bandwidth利用率。 下面&#xff0c;我以5870為例&#xff0c;探討一下如何計算得到這些結果&#xff1a; L1 c…

Docker : Dockerfile 定制鏡像

使用 Dockerfile 定制鏡像 前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 鏡像的定制實際上就是定制每一層所添加的配置、文件。如果我們可以把每一層修改、安裝、構建、操作的命令都寫…

動態規劃 最長上升子序列

題意&#xff1a;給出一個序列&#xff0c;求它的最長上升子序列的長度 題目鏈接&#xff1a;https://ac.nowcoder.com/acm/problem/26156 輸入:n代表長度&#xff0c;然后是一個字符串 分析&#xff1a;用dp[i]表示長度為i1的上升子序列末尾元素的最小值&#xff08;一開始初始…

解說redis中如何實現高可用

redis中為了實現高可用&#xff08;High Availability&#xff0c;簡稱HA&#xff09;&#xff0c;采用了如下兩個方式&#xff1a;主從復制數據。采用哨兵監控數據節點的運行情況&#xff0c;一旦主節點出現問題由從節點頂上繼續進行服務。主從復制redis中主從節點復制數據有全…

OpenCL memory object 之 Global memory (1)

這篇日志是學習AMD OpenCL文檔時候的總結。 OpenCL用memory object在host和device之間傳輸數據&#xff0c;memory object由runtime&#xff08;運行庫&#xff0c;driver的一部分&#xff09;來管理。 OpenCL中的內存對象包括buffer以及image&#xff0c;buffer是一維數據元素…

Docker: dockerfile 使用介紹

Docker簡介 前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 Docker項目提供了構建在Linux內核功能之上&#xff0c;協同在一起的的高級工具。其目標是幫助開發和運維人員更容易地跨系統跨…

【Hello CSS】第六章-文檔流與排版

作者&#xff1a;陳大魚頭github&#xff1a; KRISACHAN正常流 什么是“正常流”&#xff1f; 其實就是我們日常所說的“文檔流”。 在W3C官方文檔里對應的是“normal flow”。 正常流的盒子屬于格式化上下文(FC)&#xff0c;在CSS2.2中可以是表格、塊或內聯。 在CSS3中引入了f…

創建型模式---工廠模式

工廠模式 在工廠設計模式中&#xff0c;客戶端可以請求一個對象&#xff0c;而無需要知道這個對象來自哪里&#xff0c;也就是使用哪個類來生成這個對象。工廠背后的思想是簡化對象的創建。與客戶端自己基于類實例化直接創建對象相比&#xff0c;基于一個中心化函數來實現&…

OpenCL memory object 之 Global memory (2)

當我們用clCreateBuffer, clCreateImage創建OpenCL memory object時候&#xff0c;我們需要輸入一個flag參數&#xff0c;這個參數決定memory object的位置。 cl_mem clCreateBuffer (cl_context context, cl_mem_flags flags, size_t size, void *host_ptr, cl_int *errc…

數據結構進階篇-跳表

大家想必都知道&#xff0c;數組和鏈表的搜索操作的時間復雜度都是O(N)的&#xff0c;在數據量大的時候是非常耗時的。對于數組來說&#xff0c;我們可以先排序&#xff0c;然后使用二分搜索&#xff0c;就能夠將時間復雜度降低到O(logN)&#xff0c;但是有序數組的插入是一個O…

查看本機ssh公鑰,生成公鑰

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 查看ssh公鑰方法&#xff1a; 1.通過命令窗口&#xff1a;打開你的git bash 窗口&#xff0c;進入.ssh目錄&#xff1a;cd ~/.ssh&…

如何實現動態水球圖 --》 echars結合echarts-liquidfill實現

1&#xff09;項目中作為項目依賴&#xff0c;安裝到項目當中(注意必須要結合echars) npm install echarts vue-echarts --save npm install echarts-liquidfill --save 2&#xff09;在需要使用水晶球的組件里引入liquidFill.js import echarts-liquidfill/src/liquidFill.js;…

OpenCL memory object 之選擇傳輸path

對應用程序來說&#xff0c;選擇合適的memory object傳輸path可以有效提高程序性能。 下面先看一寫buffer bandwidth的例子&#xff1a; 1. clEnqueueWriteBuffer()以及clEnqueueReadBuffer() 如果應用程序已經通過malloc 或者mmap分配內存&#xff0c;CL_MEM_USE_HOST_PTR是個…

struts入門超詳細

https://blog.csdn.net/yerenyuan_pku/article/details/52652262轉載于:https://www.cnblogs.com/liuna369-4369/p/10870873.html

RabbitMQ 從入門到精通 (一)

目錄 1. 初識RabbitMQ2. AMQP3.RabbitMQ的極速入門4. Exchange(交換機)詳解4.1 Direct Exchange4.2 Topic Exchange4.3 Fanout Exchange5. Message 消息1. 初識RabbitMQ RabbitMQ 是一個開源的消息代理和隊列服務器&#xff0c;用來通過普通協議在完全不同的應用之間共享數據&a…

接收并解析消息體傳參、解析 json 參數

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 1.場景&#xff1a;postman 發送了一個 post 請求&#xff0c;如下&#xff1a; 2. 解析方式為用一個 vo 對象來接收 json。把 json 中的…

OpenCL memory object 之 傳輸優化

首先我們了解一些優化時候的術語及其定義&#xff1a; 1、deferred allocation&#xff08;延遲分配&#xff09;&#xff0c; 在第一次使用memory object傳輸數據時&#xff0c;runtime才對memory object真正分配空間。 這樣減少了資源浪費&#xff0c;但第一次使用時要慢一些…