vectorize calculation of 3 for

1 view (last 30 days)
Robin L.
Robin L. on 8 Mar 2019
Commented: Robin L. on 8 Mar 2019
Hello !
Let us take 3 vectors 1D :
vectors L, M and N
% let us take L, M, N, 3 matrix 1D
for Lidx = 1:length(L)
for Midx = 1:length(M)
for Nidx = 1:length(N)
tab(Lidx, Midx, Nidx) = L(Lidx)*M(Midx)*N(Nidx);
end
end
end
How can I optimize that ?
I found myself a solution :
L_repmat = repmat(L, 1, length(M), length(N));
N_3d = permute(N, [3 1 2]);
N_3d_repmat = repmat(N_3d, length(L), length(M));
vectorized = L_repmat.*N_3d_repmat;
I works nicely, but is there a more optimized way ?
Robin ?

Accepted Answer

John D'Errico
John D'Errico on 8 Mar 2019
It works, and is already vectorized. Could you have used meshgrid or ndgrid to do the same? Well, yes. Would it be any better? Well, most of the gain was achieved already when you wrote the vectorized code.
A really big problem with the looped code that you wrote was the fact you had not preallocated tab. As cuh, MATLAb is now forced to grow that array dynamically MANY times. If the vectors are long, this will be a big time waster.
The only issue with the repmats is they actually allocate memory that can grow large, if L,M,N have thousands of elements.
Here is a way to write it without the repmats, reshapes, and permutes.
[LL,MM,NN] = ndgrid(L,M,N);
tab = LL.*MM.*NN;
So, as a test, we could do this:
L = 1:3;
M = 1:4;
N = 1:5;
[LL,MM,NN] = ndgrid(L,M,N);
tab = LL.*MM.*NN;
size(tab)
ans =
3 4 5
But, the above call to ndgrid also creates arrays that are fairly large.
If you have a more recent release of MATLAB (thus R2016b or later), then you could have done this without even a call to ndgrid, and with no large intermediate array creation.
tab = L(:) .* M(:).' .* reshape(N,[1 1 numel(N)]);
size(tab)
ans =
3 4 5
Older releases of MATLAB would use bsxfun.
Are any of these expedients truly necessary, unless the vectors are pretty large? Well, it depends on the size of the vectors. Preallocating your array tab for the looped code would have made that code already pretty efficient. Is the final version I wrote the best? Yes, probably so, because MATLAB is able to do all the hard work internally and efficiently.
  1 Comment
Robin L.
Robin L. on 8 Mar 2019
Thank you John D'Errico !
I did some performance tests and with big matrix my second solution takes too much time (30 x more than the 3 for), as well as your ndgrid solution.
But with reshape it is perfect, thank to you !

Sign in to comment.

More Answers (0)

Products

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!