Using a function instead of inlining increases the time it takes to run

1 view (last 30 days)
Jori on 15 Dec 2014
Commented: Jori on 16 Dec 2014
I use 64-bit Matlab R2014b.
I have a large matrix in which I iteratively change one element and I have another operation in which I sort a smaller matrix. I have two minimal working examples and I would like to know why one approach takes longer than the other. The first example uses a direct approach, whereas the second approach uses a function to perform the task.
Minimal working example 1
n_iter = 1e7;
A = zeros(n_iter,1);
B = sort(rand(1e3,1));
for i = 1:n_iter
A(i) = 1;
B = sort([ B(2:end); B(1) ]);
end
Minimal working example 2
function deallocating_large_matrices_function
n_iter = 1e7;
A = zeros(n_iter,1);
B = sort(rand(1e3,1));
for i = 1:n_iter
A(i) = 1;
B = sortB(B(2:end),B(1));
end
end
function B = sortB(B,new_entry)
B = sort([ B ; new_entry ]);
end
Results
Below a table showing the time it took to run both examples as a function of n_iter, using the profiler.
n_iter | time MWE 1 (sec) | time MWE 2 (sec)
--------------------------------------------
1e4 | 0.13 | 0.21
1e5 | 1.38 | 1.98
1e6 | 13.5 | 19.7
1e7 | 137 | 196
The time it takes to run both MWE 1 and MWE2 increases linearly. Running MWE 2 takes approximately 46% more time. What is the cause of this increase?
3 CommentsShow 1 older commentHide 1 older comment
Jori on 15 Dec 2014
Thanks Adam for your comment. Just for clarity, MWE 2 is just one .m-file.
With regards to your third paragraph, I was thinking that it indeed had something to do with that. I assume that the function sortB stores it arguments (B and new_entry) in a separate slot in memory, since these are local variables to the function sortB. Is it possible that at the end of every iteration, Matlab needs to deallocate the memory that the function sortB uses? This then also explains the increase of 46% for every number of iterations.
Adam on 15 Dec 2014
As far as I am aware it will recreate the function's workspace every call, although I don't know what kind of optimisations of the code take place at runtime - it may be clever enough to optimise that away.
I think new_entry in your above code will not take up any new memory, but B will, in your subfunction. This is because even though Matlab passes data by value rather than by reference, it is clever enough to not take a physical copy of data until or unless that data changes in your sub-function. At that point it will allocate memory and copy the data into it since it can't refer to the original any more.
If a variable is just input to a function, but remains unchanged in that function I am fairly sure no new memory is allocated to it and it just refers to the original in memory. I may be wrong there though and someone will hopefully correct me if I am.

Amit on 15 Dec 2014
The issue is in subfunction
function B = sortB(B,new_entry)
B = sort([ B ; new_entry ]);
end
You are passing a vector of size 'n-1' as B and the returning the same variable B but with size 'n'. This requires rewriting and reallocating memory, in other words more time!
Try this: function deallocating_large_matrices_function
n_iter = 1e7;
A = zeros(n_iter,1);
B = sort(rand(1e3,1));
for i = 1:n_iter
A(i) = 1;
B = sortB([B(2:end);B(1)]);
end
end
function B = sortB(B)
B = sort(B);
end
This will result in more comparable time.
Jori on 16 Dec 2014
This shaved the time down to a mere 7% increase. Thank you for your answer.

Categories

Find more on Logical in Help Center and File Exchange

Community Treasure Hunt

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

Start Hunting!