1. 程式人生 > >像寫C++一樣寫CUDA

像寫C++一樣寫CUDA

https://github.com/Matazure/tensor
Tensor是一個基於C++, CUDA的異構計算庫,其上層介面極大地提高了高效能異構程式的開發效率。Tensor採用C++ AMP,Thrust的異構介面設計;具備類似Matlab的基本矩陣操作;將Eigen的延遲計算推廣到GPU端;使用超程式設計技術追求擴充套件性和效能的極致。Tensor將致力於為眾多異構應用提供底層支援。

特點

  • 統一的異構程式設計介面
  • 泛型設計,超程式設計支援
  • 記憶體自動回收
  • 向量化操作
  • 延遲計算
  • Header only
  • 多平臺支援

示例

下面的程式演示如何使用Tensor庫對兩個tensor進行相加

#include <matazure/tensor>
using namespace matazure;

float main(){
    //申請裝置端tensor
    cuda::tensor<float, 1> ts0(5);
    cuda::tensor<float, 1> ts1(ts0.shape());    
    //為tensor賦值
    //__matazure__關鍵字用於宣告此lambda運算元可以在cuda中執行
    cuda::for_index(0, ts0.size(), [=] __matazure__ (int_t i){
        ts0[i] = static_cast
<float>(i); ts1[i] = i * 0.1f; }); //將ts0加ts1的結果存入ts2中 cuda::tensor<float, 1> ts2(ts0.shape()); cuda::for_index(0, ts0.size(), [=] __matazure__ (int_t i){ ts2[i] = ts0[i] + ts1[i]; }); //列印結果 cuda::for_index(0, ts2.size(), [=] __matazure__ (int_t i){ printf
("%d : %f\n", i, ts2[i]); }); //等待裝置端的任務執行完畢 cuda::device_synchronize(); return 0; }

可以看出,使用Tensor庫,異構程式的開發效率可以獲得極大的提升。下面的異構程式用於rgb影象歸一化並分離三個通道的資料

#include <matazure/tensor>
using namespace matazure;

//若支援CUDA則使用
#ifdef MATAZURE_CUDA
#define WITH_CUDA
#endif

int main(int argc, char *argv[]) {
    //定義3個位元組的rgb型別
    typedef point<byte, 3> rgb;
    //定義rbg影象
    tensor<rgb, 2> ts_rgb(512, 512);
    //將raw資料載入到ts_rgb中來
    io::read_raw_data("data/lena_rgb888_512x512.raw_data", ts_rgb);
    //選擇是否使用CUDA
#ifdef WITH_CUDA
    auto gts_rgb = mem_clone(ts_rgb, device_t{});
#else
    auto &gts_rgb = ts_rgb;
#endif
    //影象畫素歸一化
    auto glts_rgb_shift_zero = gts_rgb - rgb::all(128);
    auto glts_rgb_stride = stride(glts_rgb_shift_zero, 2);
    auto glts_rgb_normalized = tensor_cast<pointf<3>>(glts_rgb_stride) / pointf<3>::all(128.0f);
    //前面並未進行實質的計算,這一步將上面的運算合併處理並把結果寫入到memory中, 避免了額外的記憶體開銷
    auto gts_rgb_normalized = glts_rgb_normalized.persist();
#ifdef WITH_CUDA
    cuda::device_synchronize();
    auto ts_rgb_normalized = mem_clone(gts_rgb_normalized, host_t{});
#else
    auto &ts_rgb_normalized = gts_rgb_normalized;
#endif
    //定義三個通道的影象資料
    tensor<float, 2> ts_red(ts_rgb_normalized.shape());
    tensor<float, 2> ts_green(ts_rgb_normalized.shape());
    tensor<float, 2> ts_blue(ts_rgb_normalized.shape());
    //zip操作,就返回tuple資料,tuple的元素為上面三個通道對應元素的引用
    auto ts_zip_rgb = zip(ts_red, ts_green, ts_blue);
    //讓tuple元素可以和point<byte, 3>可以相互轉換
    auto ts_zip_point = point_view(ts_zip_rgb);
    //拷貝結果到ts_red, ts_green, ts_blue中,因為ts_zip_point的元素是指向這三個通道的引用
    copy(ts_rgb_normalized, ts_zip_point);
    //儲存raw資料
    io::write_raw_data("data/lena_red_float_256x256.raw_data", ts_red);
    io::write_raw_data("data/lena_green_float_256x256.raw_data", ts_green);
    io::write_raw_data("data/lena_blue_float_256x256.raw_data", ts_blue);

    return 0;
}

豐富的tensor操作,向量化的介面使程式碼看起來清晰整潔,延遲計算的使用,避免了額外的記憶體讀寫,讓程式擁有極佳的效能。

開發環境

僅CPU支援

Tensor的程式碼規範遵循C++11標準, 所以只需編譯器支援C++11即可。

CUDA支援

在符合CPU支援的基礎上,需要安裝CUDA 8.0,詳情可檢視CUDA官方文件

生成專案

先安裝gitCMake,然後在命令列裡執行

Linux

git clone --recursive https://github.com/Matazure/tensor.git
mkdir build
cd build
cmake ..

Windows

git clone --recursive https://github.com/Matazure/tensor.git
mkdir build
cd build
cmake .. -G "Visual Studio 14 2015 Win64"

使用

git clone https://github.com/Matazure/tensor.git

使用上面指令獲取tensor專案後,將根目錄(預設是tensor)加入到目標專案的標頭檔案路徑即可,無需其他庫檔案依賴。有關C++專案,或者CUDA專案的建立,可自行查閱網上眾多的資源。

工具

為了儘可能的減少第三方庫的依賴,示例會直接使用raw資料,我們可以藉助ImageMagic來轉換影象和raw資料
將影象轉換為raw資料

convert   lena_rgb888_512x512.jpg  -depth 8 rgb:lena_rgb888_512x512.raw_data
convert   lena_rgb888_512x512.jpg  -depth 8 gray:lena_gray8_512x512.raw_data

將raw資料轉換為影象

convert  -size 512x512 -depth 8 rgb:lena_rgb888_512x512.raw_data lena_rgb888_512x512.jpg
convert  -size 512x512 -depth 8 gray:lena_gray8_512x512.raw_data lena_gray8_512x512.jpg

許可證書

該專案使用MIT證書授權,具體可檢視LICENSE檔案

聯絡方式

原作者希望更多的人加入到Tensor的使用開發中來,若在使用上有迷惑的地方,可直接通過郵件聯絡,週末可加QQ溝通
郵箱: [email protected]
QQ: 417083997

相關推薦

C++一樣CUDA

https://github.com/Matazure/tensor Tensor是一個基於C++, CUDA的異構計算庫,其上層介面極大地提高了高效能異構程式的開發效率。Tensor採用C++ AMP,Thrust的異構介面設計;具備類似Matlab的基

一樣代碼,玩遊戲一樣的開心心情,還能領工資!

完全 自己 沒有 深入 興趣 靈魂 一個 遊戲 好代碼 [軟]上海-Qt俠 2017/7/12 16:11:20我完全是興趣主導,老板不給我錢,我也要寫好代碼!白天幹,晚上幹,周一周五幹,周末繼續幹!編程已經深入我的基因,深入我的骨髓,深入我的靈魂!當我解決一個程序問題,比

大牛一樣程式碼: 31個Android 開發者工具

編輯推薦:稀土掘金,這是一個針對技術開發者的一個應用,你可以在掘金上獲取最新最優質的技術乾貨,不僅僅是Android知識、前端、後端以至於產品和設計都有涉獵,想成為全棧工程師的朋友不要錯過! 這是一個幫助你跟蹤app整體效能的工具,深入分析關鍵的效能資料如FPS,

C語言一個好玩的寶石一樣的圖

循環圖像圖形#include<stdio.h>main(){int n;scanf("%d",&n); for(int i=0;i<n;i++) { for(int j=0;j<n-i-1;j++) { printf(" ")

使用ES6新陣列方法(象C# Lambda表示式一樣查詢語句)

let people = [ {id: 1, name: "a", age: 12}, {id: 2, name: "b", age: 13}, {id: 3, name: "c", age: 14}, {id: 4, name: "d", age: 15}

使用ES6新數組方法(象C# Lambda表達式一樣查詢語句)

java true lte light let 重寫 ava con 表達 let people = [ {id: 1, name: "a", age: 12}, {id: 2, name: "b", age: 13}, {id: 3,

Markdown費事?Typora讓你word一樣行雲流水,所見即所得。

Typora 簡介 Typora刪除了預覽視窗,以及所有其他不必要的干擾。取而代之的是實時預覽。 Markdown的語法因不同的解析器或編輯器而異,Typora使用的是GitHub Flavored Markdown。 下載 Typora下載。 常用快捷鍵 加粗: 

如何在python專案中Django中一樣功能的settings

一  核心檔案目錄結構 二  實現程式碼 resdme:   在實現此功能主要用到的知識點及模組:   1.反射   2.importlib模組   3.內建方法dir # 全域性配置 name = 'personal' 全域性配置

如何在python項目中Django中一樣功能的settings

文件目錄 config 存在 alt elf 功能 int 顯示 att 一 核心文件目錄結構 二 實現代碼 resdme:   在實現此功能主要用到的知識點及模塊:   1.反射   3.內置方法dir # 全局配置 NAME = ‘roo

【Python實戰】Pandas:讓你SQL一樣做資料分析(二)

1. 引言 前一篇介紹了Pandas實現簡單的SQL操作,本篇中將主要介紹一些相對複雜一點的操作。為了方便後面實操,先給出一份簡化版的裝置統計資料: 0 android NLL 387546520 2099457911 0 ios NLL 52877990 916421755 1 and

【Python實戰】Pandas:讓你SQL一樣做資料分析(一)

1. 引言 Pandas是一個開源的Python資料分析庫。Pandas把結構化資料分為了三類: Series,1維序列,可視作為沒有column名的、只有一個column的DataFrame; DataFrame,同Spark SQL中的DataFrame一樣,其概念來自於R語言,為多column並sch

對映檔案到記憶體,操作記憶體一樣方便讀檔案——MemFile

編碼中操作檔案是常有的事,本文封裝了一種不一樣的讀寫檔案方式,通過對映檔案可以想操作記憶體一樣方便的讀寫檔案。 方法解釋: Attach:關聯已存在的檔案並對映到記憶體,不存在返回NULL; Detach:取消關聯機器對映; Alloc:建立一個新的檔案並對映到記憶體; C

Flutter一樣開發Android原生應用

要問到Flutter和Android原生App,在開發是有何區別,程式設計方式是繞不開的話題。Flutter採用宣告式程式設計,Android原生開發則採用指令式程式設計。 ## 宣告式程式設計 VS. 指令式程式設計 我們首先要明確的,是何為宣告式程式設計,何為指令式程式設計。 ### 何為宣告

GDI+下Bitmap逐素快速讀性能測試

public 技術 技巧 寫在前面的話:本文針對GDI+下Bitmap操作(Get/SetPixel)進行測試,而非尋求最快速的位圖處理方式。如果你需要速度上的提升,請使用GDI+以外的技術,如並行計算、調用MMX/SSE指令、CUDA等。這是一個古老的技巧:使用Bitmap類時經常會用到GetP

c文件

inpu r+ class rac repo clas ptr out from 整理一波c讀寫文件的API。 fopen FILE * fopen ( const char * filename, const char * mode ); 打開模式有以下幾種:

c#讀Xml文件

引用 use 記錄 一行 tar desktop for 單個 contacts 寫入xml文件 第一種方法:使用XmlDocument類: Demo1 //通過代碼創建XML文檔 //1、引用命名空間 System.Xml

C# 讀App.config配置文件的方法

命名 csdn ini 手工 讀寫 xml文件 strong 我們 異常 一、配置文件概述: 應用程序配置文件是標準的 XML 文件,XML 標記和屬性是區分大小寫的。它是可以按需要更改的,開發人員可以使用配置文件來更改設置,而不必重編譯應用程序。配置文件的根節點是con

C# 中得很不錯的一段代碼摘出來

spa edi model png off callback 代碼 iss back private void LikeMyworkEvent(EditedImg img, bool islike) //點贊自己的作品 { if (Applica

C語言單鏈表的創建、釋放、追加(即總是在最後的位置增加節點)

程序 mage 而不是 自己的 物理 2-66 exit 只為 對數 昨天周末給學妹講了一些指針的知識,本來我對指針就是似懂非懂的狀態,經過昨天一講,我對指針的學習就更深刻了果然給別人講課也是學習的一個方法。加上最近復習數據結構,發現我的博客裏沒有鏈表的博文,

c# 讀ini文件

log summary size 寫入 gpo static stringbu eprof profile //在 Ini 文件中寫數據 [DllImport("kernel32")] private static extern long Wri