MATLAB上的GPU加速計算——學習筆記 (2014-12-22 04:44:05)
轉自:http://blog.sina.com.cn/s/blog_6f062c360102v9ic.html
MATLAB可謂工程計算中的神器,一方面它自帶豐富的函式庫,另一方面它所有的資料都是內建的矩陣型別,最後畫圖也方便,因此解決一些小規模的計算問題如果對效能要求不高的話開發效率遠大於C++ FORTRAN之類傳統手段。不過受限於PC的計算能力,對於一些大規模資料處理它就力不從心了。還好最近Matlab開發了cuda的wrapper,計算能力因而上升了一個數量級。
那麼怎樣在MATLAB上做GPU計算呢?
首先要進行資料的初始化。有兩種方法可以進行初始化:一是先在CPU上設定好資料然後拷貝到GPU;二是直接在GPU上初始化資料。先看看第一種方案:
N = 6;
M = magic(N);
G = gpuArray(M);
可見把資料從CPU拷貝到GPU上非常簡單,只要B = gpuArray (A)就可以了。實際上MATLAB並沒有規定一個矩陣定義之後不能改型別,所以以下也是可以的:
M = gpuArray(M);
有時候GPU受限於硬體架構,單精度的計算遠快於雙精度。這時候可以考慮在拷貝的時候順便轉換一下精度:
A = gpuArray(single(B));
如前所述,第二種方法是直接在GPU上設定資料:
A = zeros(10, 'gpuArray');
這時候執行size函式:
size (A)
得到 100 100。所以A其實是一個二維陣列。
也可以生成一個一維的隨機陣列:
r = gpuArray.rand(1, 100) % 一行,一百列
執行class函式:
class(r)
得到
ans = gpuArray。可見這是一個在gpu上的陣列。
下面就是對GPU資料進行操作。首先,MATLAB定義了GPU上豐富的庫函式,比如快速傅立葉變換:
result = fft(r)
這樣result就是另一個GPU上的陣列,儲存了對r做fft的結果。
加減乘除更不在話下:
r2 = (real(result) + r ) / 2
作用是對result取實部之後加r再除以2.這裡r2, r, result都是GPU上的陣列。方便吧?
最後是如何把GPU上的資料回傳給CPU:
B = gather (A);
其中A是GPU上的資料,B是CPU上的資料。B的內容在回傳之後等於A。
並不是所有的電腦都可以用MATLAB進行GPU加速計算。想知道自己的電腦有沒有這個能力,執行gpuDevice:
>> gpuDevice
ans =
CUDADevice with properties:
Name: 'GeForce GTX 650'
Index: 1
ComputeCapability: '3.0'
SupportsDouble: 1
DriverVersion: 6.5000
ToolkitVersion: 5
MaxThreadsPerBlock: 1024
MaxShmemPerBlock: 49152
MaxThreadBlockSize: [1024 1024 64]
MaxGridSize: [2.1475e+09 65535 65535]
SIMDWidth: 32
TotalMemory: 1.0737e+09
FreeMemory: 732377088
MultiprocessorCount: 2
ClockRateKHz: 1058500
ComputeMode: 'Default'
GPUOverlapsTransfers: 1
KernelExecutionTimeout: 1
CanMapHostMemory: 1
DeviceSupported: 1
DeviceSelected: 1
MATLAB目前只支援Nvidia的顯示卡。如果你的顯示卡是AMD的或者是Intel的,就得考慮另尋它路了。