6

Matlab のベクトル化されたコードは、for ループよりもはるかに高速に実行されます ( 1 台のマシンでの Octave での並列計算 - Octave での具体的な結果のパッケージと例を参照してください)。

そうは言っても、次に示すコードを Matlab または Octave でベクトル化する方法はありますか?

x = -2:0.01:2;
y = -2:0.01:2;
[xx,yy] = meshgrid(x,y);
z = sin(xx.^2-yy.^2);
4

3 に答える 3

6

とのベクトルmeshgridndgrid

問題のベース コードを高速化するためのベクトル化された実装を見つけることに引き続き関心がある場合は、GPU 移植版のmeshgridベクトル化方法を提案させてください。コードを高速化するための有望なオプションとして、bsxfun人々が検討する必要があると強く信じています。orを使用するコードや、その出力が要素ごとの操作セットアップで操作されるコードは、それらのコードに使用するのに最適な基盤です。それに加えて、利用可能な数百、数千の CUDA コアを使用して要素を独立して処理できる GPU を使用すると、GPU の実装に最適です。vectorization with GPUsMATLABmeshgridndgridbsxfunbsxfun

特定の問題について、入力は-

x = -2:0.01:2;
y = -2:0.01:2;

次に、あなたは-

[xx,yy] = meshgrid(x,y);
z = sin(xx.^2-yy.^2);

bsxfun、これはワンライナーになります -

z = sin(bsxfun(@minus,x.^2,y.^2.'));

ベンチマーク

GPU ベンチマークのヒントは、GPU パフォーマンスの測定と改善から引用されました。

%// Warm up GPU call with insignificant small scalar inputs
temp1 = sin_sqdiff_vect2(0,0);

N_arr = [50 100 200 500 1000 2000 3000]; %// array elements for N (datasize)
timeall = zeros(3,numel(N_arr));

for k = 1:numel(N_arr)
    N = N_arr(k);
    x = linspace(-20,20,N);
    y = linspace(-20,20,N);

    f = @() sin_sqdiff_org(x,y);%// Original CPU code
    timeall(1,k) = timeit(f);
    clear f

    f = @() sin_sqdiff_vect1(x,y);%// Vectorized CPU code
    timeall(2,k) = timeit(f);
    clear f

    f = @() sin_sqdiff_vect2(x,y);%// Vectorized GPU(GTX 750Ti) code
    timeall(3,k) = gputimeit(f);
    clear f
end

%// Display benchmark results
figure,hold on, grid on
plot(N_arr,timeall(1,:),'-b.')
plot(N_arr,timeall(2,:),'-ro')
plot(N_arr,timeall(3,:),'-kx')
legend('Original CPU','Vectorized CPU','Vectorized GPU (GTX 750 Ti)')
xlabel('Datasize (N) ->'),ylabel('Time(sec) ->')

関連機能

%// Original code
function z = sin_sqdiff_org(x,y)
[xx,yy] = meshgrid(x,y);
z = sin(xx.^2-yy.^2);
return;

%// Vectorized CPU code
function z = sin_sqdiff_vect1(x,y)
z = sin(bsxfun(@minus,x.^2,y.^2.')); %//'
return;

%// Vectorized GPU code
function z = sin_sqdiff_vect2(x,y)
gx = gpuArray(x);
gy = gpuArray(y);
gz = sin(bsxfun(@minus,gx.^2,gy.^2.')); %//'
z =  gather(gz);
return;

結果

ここに画像の説明を入力

結論

結果が示すように、GPU を使用したベクトル化された方法は4.3x、ベクトル化された CPU コードと6x元のコードに対してほぼ同等の良好なパフォーマンスの改善を示しています。GPU は、セットアップに必要な最小限のオーバーヘッドを克服する必要があることに注意してください。そのため、改善を確認するには、少なくとも適切なサイズの入力が必要です。うまくいけば、人々は をもっと探求してくれるでしょうvectorization with GPUs

于 2014-08-06T13:58:24.093 に答える
5

Matlabでは、組み込みのベクトル化された関数をマルチスレッドに変換する唯一の方法は、MathWorksがそれらをそのように実装するのを待つことです。

または、ベクトル化された計算をループとして記述し、を使用してそれらを並列に実行することもできますparfor

最後に、多くの関数がGPU対応であるため、並列処理ツールボックスにアクセスすることで、減算や要素ごとのパワーなど、これらの操作を並列化できます。

于 2012-05-11T01:16:44.927 に答える