生成重复值序列的向量,每个值的给定出现次数

Pro*_*gma 7 matlab

我想实现以下功能:

输入:

  1. 矢量的价值观

  2. 相同大小的向量,说明每个值(相应索引)的出现次数应该在输出向量中.

输出:

重复序列中值1by1的向量,其中每个值显示为所需的出现次数.

值将继续显示为1by1,直到某个值根据需要出现多次,然后其余值将在没有它的情况下继续显示.

例:

输入:

  1. [1,2,3,4]

  2. [3,2,5,1]

输出:[1 2 3 4 1 2 3 1 3 3 3]

通缉解决方案:

我想找到一个简单的解决方案,但不使用任何循环,并且对任何长度的输入向量都是模块化的.

当前解决方案

到目前为止,只能实现循环或不愉快的索引.循环解决方案如下:

双循环:

vals_vec=1:4;
occur_vec=[3,2,5,1];
output_vec=zeros(1,sum(occur_vec));
num_of_vals=length(vals_vec);
output_i=1;

while (output_i<=length(output_vec)) % While in length of output vector
    for cur_val_i=1:num_of_vals % Loop over all values
        if(occur_vec(cur_val_i)>0) % If value hasn't reached its occurrence number
            occur_vec(cur_val_i)=occur_vec(cur_val_i)-1;
            output_vec(output_i)=vals_vec(cur_val_i);
            output_i=output_i+1;
        end

    end
end
output_vec
Run Code Online (Sandbox Code Playgroud)

单回路:

vals_vec=1:4;
occur_vec=[3,2,5,1];
output_vec=[];

for cur_num_of_vals=length(vals_vec):-1:1
    [min_val,min_i]=min(occur_vec); % Find lowest occurrence number
    output_vec=[output_vec,repmat(vals_vec,1,min_val)]; % Add vals accordingly
    vals_vec=[vals_vec(1:min_i-1),vals_vec(min_i+1:cur_num_of_vals)]; % Remove the corresponding val
    occur_vec=occur_vec-min_val; % Reduce Occurences from all vals
    occur_vec=[occur_vec(1:min_i-1),occur_vec(min_i+1:cur_num_of_vals)]; % Remove the corresponding occurrence number
end

output_vec
Run Code Online (Sandbox Code Playgroud)

谢谢!

Wol*_*fie 5

您可以通过过度复制输入,然后删除多余的重复来完成此操作.

编辑:这是一个没有循环的解决方案:

% Repeat array to max number of possible repetitions
out = repmat( vals, 1, max(reps) ); 
% Implicit expansion (requires R2016b or newer, otherwise use bsxfun) to create
% matrix of reducing repetition count, then remove repeated values
% where this is <= 0, i.e. where there are no repetitions remaining.
out(reshape( reps' - (0:max(reps)-1), 1, [] ) <= 0) = [];

% Pre-R2016b version would be 
% out(reshape( bsxfun(@minus, reps', (0:max(reps)-1)), 1, [] ) <= 0) = [];
Run Code Online (Sandbox Code Playgroud)

原文:需要一个循环,但输入值不是输出数组,所以它至少是一个短的...

vals = [1,2,3,4];
reps = [3,2,5,1];
out = repmat( vals, 1, max(reps) ); % repeat array to max number of possible repetitions
for ii = 1:numel(vals)
    % Remove elements which have appeared too many times
    out( out == vals(ii) & (cumsum(out==vals(ii)) > reps(ii)) ) = [];
end
Run Code Online (Sandbox Code Playgroud)