4
votes

I have this sparse matrix of the following form

Lets take an example of 5x10 matrix

      1  2  3  4  5  6  7  8  9  10
 1    1  1  0  0  0  0  0  0  0   0
 2    0  1  0  0  0  0  0  0  0   0
 3    .............................
 4    .............................
 5    .............................

From this sparse matrix, I want to create a cell array C of form

C{1} 1
C{2} = [1,2]
...........
...........
...........

My sparse matrix is high dimensional like 40000 by 790000. How can I do it efficiently in matlab. I can definitely use a loop and do it inefficiently. But I want the most efficient. Suggestions?

2

2 Answers

2
votes

Use find to get the indices and accumarray to group them by columns:

[ii, jj] = find(A);
C = accumarray(jj, ii, [], @(v) {v.'});

Benchmarking

%// Random sparse matrix. Code adapted from @teng's answer
sz = [4e4 79e4];
nz = 1e5; %// number of nonzeros
A = sparse(randi(sz(1),[nz 1]),randi(sz(2),[nz 1]),1,sz(1),sz(2));

tic;    
[ii, jj] = find(A);
C = accumarray(jj, ii, [], @(v) {v.'});
toc

Results:

  • For nz = 1e4:

    Elapsed time is 0.099657 seconds.
    
  • For nz = 1e5:

    Elapsed time is 0.756234 seconds.
    
  • For nz = 1e6:

    Elapsed time is 5.431427 seconds.
    
0
votes

Let me get the party started... let's start with the basics:

 tic;
 sz = [ 400 7900]; % hehe...
 aMat = sparse(randi(sz(1),[1000 1]),randi(sz(2),[1000 1]),1,sz(1),sz(2));
 aCell = mat2cell(aMat,ones([sz(1) 1]));
 preC = cellfun(@(x) x(x~=0), aCell,'UniformOutput',false);
 C = cellfun(@(x) find(x), preC,'UniformOutput',false);
 toc