Replacing nested "for" loops

Hi all,
I have a set of "K" nested "for" loops, where "K" is variable. An example of my code for when K=4 is as follows:
Spectral_eff_Points=(0):(1):(20);
S=zeros(K,1);
p=zeros(K,1);
n = length(Spectral_eff_Points);
for s1_index=1:n,
S(1)=Spectral_eff_Points(s1_index);
for s2_index=1:n,
S(2)=Spectral_eff_Points(s2_index);
for s3_index=1:n,
S(3)=Spectral_eff_Points(s3_index);
for s4_index=1:n,
S(4)=Spectral_eff_Points(s4_index);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% MAIN CALCULATIONS DONE HERE
for user_index=1:K
if user_index==1;
p(user_index)=(2^(S(user_index))-1)* (N/g(user_index));
else
increment=1:(user_index-1);
Sum_P_inc=sum(p(increment));
p(user_index)=(2^(S(user_index))-1)* ((N/g(user_index))+Sum_P_inc);
end
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
end
end
end
end
As you can see, for large "K" and "n" values, the code will be very very slow :( Does anyone have any better way of conducting such loops, but in a much faster way?!
any help will be much appreciated.
Thanks

 Accepted Answer

At first clean up the current code:
% MAIN CALCULATIONS DONE HERE
p(1) = (2^S(1) - 1) * (N/g(1)); % Avoid test for ==1 in each iteration!
tmp1 = cumsum(p);
for user_index = 2:K
Sum_P_inc = tmp1(user_index - 1);
p(user_index) = (pow2(S(user_index))-1) * (N/g(user_index) + Sum_P_inc);
end
Perhaps a vectorized version is faster:
p = (pow2(S) - 1) .* (N ./ g + [0; cumsum(p(1:end-1))]);
Please test this - I do neither have your data nor can I access Matlab currently.
In a further step you can convert the K "for" loops to 1 "while" loop by using a [1 x K] vector and increment the last element until the limit is reached. Then increment the next element and reset the last one until even the first element reaches the limit.

1 Comment

Hi Jan,
Thank you very much for your time and effort to answer my question.
Just to let you know, the "clean-up" section works, and gives the same result, however, this doesn't speed the code up much.
About your second comment, would you be able to give me a bit more detail on how to convert the K for loops to a single while loop please.
Once again, many thanks for your time.

Sign in to comment.

More Answers (1)

A code example for K "loops" represented by a [1 x K] vector:
n = 3;
K = 4;
V = ones(1, K);
go = true;
while go
% The action:
disp(V);
% Increment:
V(K) = V(K) + 1;
if V(K) > n
V(K) = 1;
go = false;
for i = K-1:-1:1
V(i) = V(i) + 1;
if V(i) <= n % i.th counter not at limit
go = true;
break; % Leave "for i" loop
end
V(i) = 1; % Reset i.th counter
end
end
end
This is choosing K elements from the vector 1:n with repetition and order.

1 Comment

Dear Jan,
You just made my day!
This is exactly what i was looking for. It is much faster than having "K" nested "for" loops, and i get the same result.
I really appreciate the time you have put into replying back to my question.
All the best

Sign in to comment.

Categories

Find more on Loops and Conditional Statements in Help Center and File Exchange

Asked:

on 8 May 2012

Community Treasure Hunt

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

Start Hunting!