MATLAB Answers

Aaron
0

CUDA: faster indexing methods than logical for large arrays?

Asked by Aaron
on 20 Mar 2013
I have a MATLAB script (a least-squares deconvolution algorithm, if you must know) which is very slow - it looks like it will take days to run on a distributed computing cluster - simply as a result of the sheer quantity of data I have to chew through.
I am trying to speed up my code using CUDA, which is looking to work brilliantly except for one piece which is still causing slowdown. I can vary the array sizes with which I am working to fit within video memory requirements, I am currently using arrays of roughly 8000*1000.
Sample code:
trian = gpuArray(zeros(8000,1000));
for k=1:300
x = some 8000*1000 gpuArray that changes each iteration of k
trian_x = trian;
M = x>-1 & x<0;
N = x>0 & x<1;
trian_x(M) = 1+x(M); % This line and the next are slow
trian_x(N) = 1-x(N);
% I then perform a few calculations on trian_x and store the result,
% this is also quite fast
end
The last two lines before the loop ends, where I assign each value trian_x such that it is 1+x for -1<x<0 and 1-x for 0<x<1, are increasing my execution times by a factor of 50 (and my CPU is bottlenecking). It seems the slowdown is where the GPU is working with the logical indexing.
If anyone has any ideas on speeding up this calculation that would be fantastic! Those two lines take 0.2 seconds to run. Multiply that by 10^7 executions and I will appreciate any speed-up to be gained!
Thanks :)

  0 Comments

Sign in to comment.

2 Answers

Answer by Ben Tordoff on 21 Mar 2013
 Accepted Answer

You can sometimes get a speed-up by replacing the logical indexing with some element-wise maths. For example:
trian_x = M.*(1+x) + (1-M).*trian_x; % Equivalent to trian_x(M) = 1+x(M)
trian_x = N.*(1-x) + (1-N).*trian_x; % Equivalent to trian_x(N) = 1-x(N)
However, this involves more operations. (Replace 1-M with ~M if you prefer.) Whether this helps will depend on problem size - I haven't tried it with your specific sizes.
Ben

  0 Comments

Sign in to comment.


Answer by Aaron
on 21 Mar 2013

Thanks for your help - that does speed things up a bit. I didn't actually realise that I could act algebraically on a logical array (I haven't used them before). Building on that, I think I've made things as fast as possible now, nearly twice as fast as before. Here is the code, in case anyone else is looking to do a triangular function or something similar with CUDA.
for k = 1:300
x = big array
trian = (x>-1 & x<0) - (x>0 & x<1);
trian_x = abs(trian)+x.*trian;
end

  0 Comments

Sign in to comment.