How to decrease the time to obtain all possible numerical combinations using the for loop in MATLAB?

Hi all,
I need to decrease the time of possible numerical combinations using for loop. In short, I am analyzing electromyography (EMG) data and doing some simulations with times among some tasks developed by office workers to see which combination creates the greatest variation in muscle. The simulations for 3 and 4 tasks didn't take me long, the problem started when I tried to get combinations for 5 tasks, I left the loop running for more than 2 hours and I still couldn't finish the combinations.
Here is my code:
% Time simulation for six tasks
% Proportion of time
% CWsit | CWstand | NCWsit | NCWstand | NonDeskW | WBreak
% CW = computer work
% NCW = Non-computer work
const = 30; % Here, I set the value 30, because my first task cannot have a value less than that
work_temp = [];
for i = 0:(90-const)
for j = 0:(90-const-i)
for k = 0:(90-const-i-j)
for l = 0:(90-const-i-j-k)
m = 90-const-i-j-k-l;
work_temp = [work_temp;[const+i j k l m]];
end
end
end
end
% note: WBreak has a fixed time of 10% (0.1 in proportion)
% Adding the Wbreak task time vector
work_temp = [work_temp, 10 + zeros(length(work_temp),1)];
Is there any way to make the loop faster?
I know that this loop will result in a huge amount of combinations, so I don't know if it helps much, but the first task cannot have more than 70% of time. (min 30 and max 70). Perhaps the loop can be stopped when get that value.
EDITED: With the help of Walter Roberson (see below) , I was able to obtain the output size, with that value I was able to make the pre-allocation.
% Finding out what matrix size do I need to store my output
const = 30;
[I, J, K, L] = ndgrid(0:90-const);
mask = J <= I & K <= J & L <= K ;
M = 90 - const - I(mask) - J(mask) - K(mask) - L(mask );
% For nested loop to simulate all possible times
const = 30;
work_temp = zeros(length(M),5); % Preallocation (save a lot of time)
c = 0;
tic
for i = 0:(90-const)
for j = 0:(90-const-i)
for k = 0:(90-const-i-j)
for l = 0:(90-const-i-j-k)
m = 90-const-i-j-k-l;
c = c + 1;
work_temp(c,:) = [const+i j k l m];
end
end
end
end
toc
Elapsed time is 0.355317 seconds.
Thanks in advance,
Luiz Augusto

3 个评论

Hint: preallocation is important. When you grow an array dynemically, it forces MATLAB to constantly increase the size of the array at EVERY iteration. That means MATLAB needs to allocate a new array of size one row larger. Then it needs to copy over the entire array, which is growing at every step.
Perhaps, more important is to ask why you feel you need to create the entire set of combinations. Perhaps there are tools that would allow you not to need to create tham at all. For example, optimization or integer linear programming might come to mind. Far too often, people seem to do things like this for no better reason than they don't know other tools exist that would solve their problem.
Thanks for your ranswer, the pre-allocation looks like what I really need. I forgot about this. I had used it once in RStudio, but I already knew the size of my output variable.
I read some comments saying that I must know the size of my output variable to make the correct pre-allocation. Is it correct?
I am still struggling to do the pre-allocation!

请先登录,再进行评论。

 采纳的回答

[I, J, K, L] = ndgrid(0:90-const);
mask = J <= I & K <= J & L <= K;
M = 90 - const - I(mask) - J(mask) - k(mask) - L(mask);

更多回答(0 个)

类别

帮助中心File Exchange 中查找有关 Loops and Conditional Statements 的更多信息

Community Treasure Hunt

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

Start Hunting!

Translated by