Help vectorize for loop please

I want to get rid of that for loop and just use/vectors/matrices, so i can optimize my code. if any one can help thanks.
%help compute the average
d = max(size(x));
c = 1/(d-1);
function y1 = f1(r)
y1 = tanh((1-r)*7) +.7;
end
%y2 will be returned
y2 = zeros(d,1);
z1 = x(1:2:2*N - 1);
z2 = x(2:2:2*N );
for j=1:(d/2)
Z1 = z1(j) - z1; %x - xj
Z2 = z2(j) - z2; %y - yj
Z3 = (Z2.*Z2) + (Z1.*Z1); %(x-xj)^2 + (y - yj)^2
Z3 = sqrt(Z3);%|X- Xj|
Z3(j) = 1;
Z1 = Z3.\Z1;% (x - xj)/|X - Xj|
Z2 = Z3.\Z2;% (y - yj)/|X - Xj|
Z4 = f1(Z3); % F( |X - Xj|)
Z1 = Z1.*Z4;%F( |X - Xj|)*(x - xj)/|X - Xj|
Z2 = Z2.*Z4;%F( |X - Xj|)*(y - yj)/|X - Xj|
y2(2*j - 1) = c*sum(Z1);
y2(2*j) = c*sum(Z2);
end

 Respuesta aceptada

Matt Tearle
Matt Tearle el 12 de Mzo. de 2011

0 votos

As far as I can tell, this seems to replace your code and is a tiny bit faster. (I tested only on small arrays, so maybe the savings will be significant on an actual problem). I assume that N = d/2? I'm also assuming that x is a column vector. I was using x = randi(10,20,1) to test, and I got the same answers as your code.
d = length(x);
c = 1/(d-1);
f1 = @(r) tanh((1-r)*7) +.7;
z1 = x(1:2:2*N - 1);
z2 = x(2:2:2*N );
y2 = zeros(d,1);
Z1 = bsxfun(@minus,z1',repmat(z1,1,d/2));
Z2 = bsxfun(@minus,z2',repmat(z2,1,d/2));
Z3 = sqrt((Z2.*Z2) + (Z1.*Z1));
Z3(1:((d/2)+1):end)=1;
Z1 = Z1./Z3;
Z2 = Z2./Z3;
Z4 = f1(Z3);
Z1 = Z1.*Z4;
Z2 = Z2.*Z4;
y2(1:2:2*N - 1) = sum(Z1)*c;
y2(2:2:2*N) = sum(Z2)*c;

4 comentarios

Emad
Emad el 12 de Mzo. de 2011
cut performance time in half, thanks I appreciate it
Emad
Emad el 12 de Mzo. de 2011
which version of matlab has JIT optimization?
Jan
Jan el 12 de Mzo. de 2011
As far as I remember the version >= 6.5 (R13) use the JIT acceleration.
Matt Tearle
Matt Tearle el 13 de Mzo. de 2011
But, like everything in MATLAB, it's being continually improved, so, generally, the later the version, the better the JIT benefits.

Iniciar sesión para comentar.

Más respuestas (1)

Matt Tearle
Matt Tearle el 11 de Mzo. de 2011

1 voto

You don't need a loop at all -- all your statements inside the loop will work as vectorized statements with virtually no modification.
Just get rid of the subscripts on the first two lines.
Delete the line Z3(j) = 1; I don't know what you were hoping this did, but I doubt it was what it actually does. Before that line, Z3 is a scalar. Then if j is 1, it just overwrites Z3. For any other j, it will make Z3 a vector of j elements. The first will be whatever Z3 was from the previous line, the last will be 1, and everything in the middle will be 0. Is that what you intended? Maybe it is, given the use of sum(Z1) later, but it's a very strange algorithm.
Finally, use indexing like you did to extract z1 and z2 from x to get the results into y2.

3 comentarios

Emad
Emad el 11 de Mzo. de 2011
The loop is necessary at the moment. Z3 is a vector. when I do Z3(j) = 1, that sets the jth element to 1 so in the next line when i do Z1 = Z3.\Z1, I will not divide by zero.irregardless of all of that. I am trying to convert the loop into a vectorized statement, since I know matlab works much better with vectors then loops for example:
if x is a vector of n elements I can find the sum by
sumofx = 0;
for i=1:n
sumofx = sumofx + x(i);
end
or I can do sumofx = sum(x);
and this computes it much more efficiently.
so I am trying to convert my loop into a vector statemnt, I know it will be difficult but i know it is possible.
Matt Tearle
Matt Tearle el 12 de Mzo. de 2011
Oops, my bad. I misread your code (all those z1s and Z2s and y2s...!) OK. Ignore everything I said. New answer coming right now.
Matt Tearle
Matt Tearle el 12 de Mzo. de 2011
BTW "I know matlab works much better with vectors then loops" is not necessarily true any more (depends on which version). Thanks to the JIT optimization, loops are now pretty quick. There are cases where you can tie yourself in knots trying to vectorize only to *lose* performance. In this case, I think you can get a bit of speed-up (see my new answer) by using matrices.

Iniciar sesión para comentar.

Preguntada:

el 11 de Mzo. de 2011

Community Treasure Hunt

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

Start Hunting!

Translated by