matlab随机排列具有相同编号的相同序列的向量元素

matlab shuffle elements of vector with the same sequent of the same number

我有以下向量 a = 3 3 5 5 20 20 20 4 4 4 2 2 2 10 10 10 6 6 1 1 1 有谁知道如何用相同的元素洗牌这个向量永远不会分开? 像下面这样的东西 a = 10 10 10 5 5 4 4 4 20 20 20 1 1 1 3 3 2 2 2 6 6 谢谢,祝好...

您可以结合使用 uniqueaccumarray 创建元胞数组,其中每组值都放置在一个单独的元胞元素中。然后您可以打乱这些元素并将它们重新组合成一个数组。

% Put each group into a separate cell of a cell array
[~, ~, ind] = unique(a);
C = accumarray(ind(:), a(:), [], @(x){x});

% Shuffle it
shuffled = C(randperm(numel(C)));

% Now make it back into a vector
out = cat(1, shuffled{:}).';

%   20 20 20  1  1  1  3  3 10 10 10  5  5  4  4  4  6  6  2  2  2

另一种选择是使用 unique 获取值,然后计算每个值出现的次数。然后您可以打乱这些值并使用 repelem 展开结果

u = unique(a);
counts = histc(a, u);

% Shuffle the values
inds = randperm(numel(u));

% Now expand out the array
out = repelem(u(inds), counts(inds));

与@Suever 非常相似的答案,使用循环和逻辑矩阵而不是单元格

a = [3 3 5 5 20 20 20 4 4 4 2 2 2 10 10 10 6 6 1 1 1];

vals = unique(a); %find unique values
vals = vals(randperm(length(vals))); %shuffle vals matrix

aout = []; %initialize output matrix
for ii = 1:length(vals)
     aout = [aout a(a==(vals(ii)))]; %add correct number of each value
end

这是另一种方法:

a = [3 3 5 5 20 20 20 4 4 4 2 2 2 10 10 10 6 6 1 1 1];
[~, ~, lab] = unique(a);
r = randperm(max(lab));
[~, ind] = sort(r(lab));
result = a(ind);

示例结果:

result =
     2  2  2  3  3  5  5 20 20 20  4  4  4 10 10 10  1  1  1  6  6

它的工作原理如下:

  1. 根据其值(这是矢量 lab)为 a 的每个元素分配唯一标签;
  2. lab的值应用随机双射(随机双射用r表示;应用它的结果是r(lab));
  3. 排序r(lab)并获取排序的索引(这是ind);
  4. 将这些索引应用于 a