Shuffling elements within the rows of a matrix
Mostrar comentarios más antiguos
Say I have a matrix, I would like to shuffle the elements within the rows randomly. For example,
A = randi(1000, 3,4)
A =
815 279 958 793
906 547 486 960
127 958 801 656
I need to get the shuffled matrix like this
B =
279 793 958 815
960 547 486 906
801 127 958 656
The most straightforward way I can think of achieving this is to use randperm to shuffle the indices of each row, and then loop over the number of rows to create the shuffled matrix. But I would like to get it all done in one go, preferably more elegantly than using a loop, because I need to do this for large matrices many times. So, alternatively, I tried this:
[nr,nc] = size(A);
P=perms(1:nc);
col_indx_mtrx = P(randi(size(P,1),nr,1),:);
ri = repmat((1:nr)',1,nc);
which gives me
ri =
1 1 1 1
2 2 2 2
3 3 3 3
col_indx_mtrx =
2 1 4 3
3 4 1 2
1 4 2 3
Now, after this, I thought if I simply do
B = A(ri,col_indx_mtrx)
I am done. But, I don't get the desired result, because when I give the row and column indices as matrices, MATLAB tries to create a matrix with all combinations of the row and column indices?
Essentially, what I need is to create the shuffled matrix B such that
B(1,1) = A(ri(1,1), col_indx_mtrx(1,1))
and so on. Is there an elegant way to achieve this last step? I tried to use arrayfun, but I could not get it done.
Or, better, is there a more elegant way of achieving the overall objective?
Any help would be greatly appreciated.
Respuesta aceptada
Más respuestas (3)
[m,n]=size(A);
T=perms(1:n); %tabulate once only
J=T(randi(m,m,1),:);
B=A( bsxfun(@plus,(1:m).', (J-1)*m) );
To achieve the last step in your code, use sub2ind:
B = A(sub2ind([nr nc], ri, col_indx_mtrx));
Jan
el 30 de Abr. de 2017
A = randi(1000, 3,4);
A1 = Shuffle(A, 1);
A2 = Shuffle(A, 2);
Categorías
Más información sobre Sparse Matrices en Centro de ayuda y File Exchange.
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!