0

I have matrix (or an array here for easier understanding), that is filled with values, e.g.:

[0 0 1 0 0 0 1 0 0 0 ]

Now I want to fill every element that is, for example 0 to a random value, but each one should be different.

If I do it like this:

replace_val = 0
x = [ 0 0 1 0 0 0 1 0 0 0 ]
x(x == replace_val) = rand

Then all 0 will be replaced with the same number, e.g.:

[ 0.8361    0.8361    1.0000    0.8361    0.8361    0.8361    1.0000    0.8361    0.8361    0.8361 ]

Now the most straight forward way is to create a loop that will iterate over the vector and at any time the condition is met, it will call the rand function like here:

for i=1:length(x)
  if x(i) == replace_val
   x(i) = rand;
  end
end

However, with matrices or very large arrays this will be very slow. So, I am wondering if there is any kind of fast, matlabish way to get the desired output?

2 Answers 2

3

This should work:

replace_val = 0
x = [ 0 0 1 0 0 0 1 0 0 0 ];
idx = x == replace_val;
x(idx) = rand(sum(idx(:)),1)

explanation: rand without input arguments will create a scalar random value. You need to specify the dimensions to obtain different random values. In order to match the number of values to be replaced, sumup the idx variable.

Hope this helps!

Sign up to request clarification or add additional context in comments.

1 Comment

As I noted below @Adrian's answer, this would be applicable for matrices with any number of dimensions if you used sum(idx(:)) or nnz(idx) instead of sum(idx) which would return a vector / matrix for any idx which isn't 1D
1

A small variation on Souty's answer, which works fine for the sample given. I wasn't comfortable with the use of sum, thinking it might cause problems if used on matrices with more than one dimension. Using logical indexing on the rand matrix allows this to be used on matrices with multiple dimensions. Also for me it is more a "matlabish" way.

% define replacement value
replace_val = 0;

% sample data
x=eye(5);

% create rand matrix same size as sample data
y = rand(size(x));

% get indices where replacement data found
idx = x == replace_val;

% use logical indexing to replace values with those from the rand array
x(idx)=y(idx);

1 Comment

Whilst you're correct that sum(idx) may cause problems with multiple dimensions, @Scouty's method could be fullproofed by simply using sum(idx(:)) or nnz(idx). You are using much more memory (esp. for large matrices) by creating y and a logical array the same size, compared to just the latter... but hey more than one way to skin a cat

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.