access time of data in cell array vs matrix
Ältere Kommentare anzeigen
Hello
I am doing operations (denoising/detection etc) on images and it seems that it is faster to store them in a cell array rather than a matrix to access them. It comes as a surpise to me. I give an exemple right under doing convolutions.
What is the reason for this ?
% create data
N_img = 1000;
img = rand(512,512,N_img);
for ii=size(img,3):-1:1
img_cell{ii}=img(:,:,ii);
end
% comparison on convolutions
tic
out_cell = img_cell;
for ii=1:N_img
out_cell{ii} = imgaussfilt(img_cell{ii});
end
toc
% I get 1.6s-1.8s
clear out_cell
tic
out_mat = img; %allocation inside or out of the timer does not change the trend
for ii=1:N_img
out_mat(:,:,ii) = imgaussfilt(img(:,:,ii));
end
toc
clear out_mat
% I get ~3.2 s
Sincerely,
1 Kommentar
I would take the imgaussfilt out of there to see the difference in access times more transparently:
% create data
N_img = 1000;
img = rand(512,512,N_img);
img_cell=num2cell(img,[1,2]);
tic
out_cell = img_cell;
for ii=1:N_img
out_cell{ii} = img_cell{ii};
end
toc
tic
out_mat = img;
for ii=1:N_img
out_mat(:,:,ii) = img(:,:,ii);
end
toc
Akzeptierte Antwort
Weitere Antworten (1)
Because extracting from cell arrays involves no new memory allocation. And because N_img=1000 is still very small.
8 Kommentare
Dyuman Joshi
am 19 Okt. 2023
"Because extracting from cell arrays involves no new memory allocation."
Matt, could you provide a reference for this?
I wouldn't know where to find one at this moment, but it's easy to test with the code below. As you can see, accessing the cell results in no drop in available memory.
%%Array Access
clear
A=rand(512,512,512);
memory().MemAvailableAllArrays/2^30
B=A(:,:,:);
memory().MemAvailableAllArrays/2^30
ans =
16.7951
ans =
15.7946
%%Cell access
clear
C={rand(512,512,512)};
memory().MemAvailableAllArrays/2^30
D=C{1};
memory().MemAvailableAllArrays/2^30
ans =
16.7966
ans =
16.7966
Matt
am 19 Okt. 2023
@Matt Yes, but allocating memory for processing output is not what differentiates the two implementations. Obviously, memory needs to be allocated to hold the output of the processing in both cases. However, you should be able to see from my test that, only in the case where you access with img(:,:,1) is new memory allocated for the input as well. A new block of memory is created to hold a copy of img(:,:,1), even before imgaussfilt or any other processing step is done.
Matt J
am 19 Okt. 2023
As an additional test, look at the following which also shows memory consumption as tracked over time with the Windows Task Manager. With cell arrays, the memory spike is half the size.
clear
A=rand(512,512,512*3);
B=A(:,:,:);
sum(B(:));
clear

%%Cell access
clear
C={rand(512,512,512*3)};
D=C{1};
sum(D(:))
clear

Matt
am 20 Okt. 2023
James Tursa
am 20 Okt. 2023
Bearbeitet: James Tursa
am 20 Okt. 2023
I doubt there is an official reference for this, but that is how it has always worked for cell and struct and property extraction. You get shallow copies (shared data or reference), not deep copies.
Walter Roberson
am 23 Okt. 2023
Bearbeitet: Matt J
am 23 Okt. 2023
https://www.mathworks.com/matlabcentral/answers/2035921-access-time-of-data-in-cell-array-vs-matrix#comment_2930491 shows it happening in practice, the same "pr"
This is an application of copy-on-write which is a fundamental MATLAB memory mechanism.
Kategorien
Mehr zu MATLAB Parallel Server finden Sie in Hilfe-Center und File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!