Random rows in matrix so no element from the first column occur twice in a row

5 visualizaciones (últimos 30 días)
Hi,
I have a matrix of x rows and 8 columns and need to random the rows so no element from the first column occur twice in a row.
It is a x times 8 double.
I know how to random the first coulumn but end up with a x times 1 array instad.
Thank you in advance

Respuesta aceptada

Adam Danz
Adam Danz el 22 de Mzo. de 2023
Editada: Adam Danz el 23 de Mzo. de 2023
There is no general solution since the values in column 1 may not sufficiently vary. For example, what if all of the values in column 1 were identical? Or what if the values in column 1 were [1;1;1;2]?
Assuming the data in column 1 sufficiently varies, you can use randperm to randomly permute the rows of the matrix. But that doesn't guarantee a lack of consecutive identical values. You could pemute the rows within a while-loop that continues to apply random permutations until the condition is satisfied or until all possibilities are exhausted, though this approach challenges the notion of randomness.
Here's a demo. If there are no permutations that satisfy the constraints, a warning is thrown (you can change that however you'd like).
rng default % for demo purposes
M = randi(3,8,3)
M = 8×3
3 3 2 3 3 3 1 1 3 3 3 3 2 3 2 1 2 1 1 3 3 2 1 3
accepted = false;
nrows = height(M);
nPossibilities = factorial(nrows); % number of possible permutations
count = 0;
while ~accepted
% If there are still consecutive identical values or
% if we ran out of possible permutations
if any(diff(M(:,1))==0) && count <= nPossibilities
pidx = randperm(nrows);
M = M(pidx,:);
count = count+1;
else
accepted = true;
% Final check: throw warning if no permutations worked.
if any(diff(M(:,1))==0)
warning('No permutations result in non-consecutive values.')
end
end
end
disp(M)
3 3 3 1 2 1 3 3 3 2 1 3 1 3 3 3 3 2 2 3 2 1 1 3
Replace the demo matrix with M = randi(2,8,3) to see the warning.
Note, if the matrix has many rows and the values in column 1 do not sufficiently vary, this could run a very long time. For example, a matrix with 10 rows has 3,628,800 possible permutations. If you expect to have this issue, you'll need a smarter solution that initially determines whether a permutation is possible.
  2 comentarios
Måns
Måns el 23 de Mzo. de 2023
Hi, Thank you for your reply. Yes the list can become fairly long, at the moment I was working on a 49 rows long matrix but it can be up towards ~800 rows long. The values will generally be in the range of 70-230.
I tried it out and it took about 10 seconds but it seems to work. Thank you very much!
Adam Danz
Adam Danz el 23 de Mzo. de 2023
If the values sufficiently vary, a permutation that satisfies the constraints should be found quickly. For example, if all values are unique, the first permutation will be accepted.

Iniciar sesión para comentar.

Más respuestas (1)

Cameron
Cameron el 22 de Mzo. de 2023
A = randi(100,5,8);
A
A = 5×8
53 42 74 79 12 36 34 40 67 49 33 93 83 60 86 45 48 93 26 6 31 41 66 64 18 12 64 87 4 30 59 36 76 96 71 46 28 97 40 42
[~,randrow] = sort(rand(size(A,1),1));
RandA = A(randrow,:)
RandA = 5×8
18 12 64 87 4 30 59 36 76 96 71 46 28 97 40 42 53 42 74 79 12 36 34 40 48 93 26 6 31 41 66 64 67 49 33 93 83 60 86 45

Categorías

Más información sobre Mathematics en Help Center y File Exchange.

Community Treasure Hunt

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

Start Hunting!

Translated by