# How to remove elements from the vector while we save the index of those removed elements?

3 views (last 30 days)
Pouya Afshin on 13 Dec 2019
Edited: Adam Danz on 17 Dec 2019
Hello, I would like to write a code inside the while loop that it removes the elements of the vector based on the criteria while it keeps the index of those removed elements in each iteration?
b=[2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 ];
y = b;
while length(y)>4
idx=find(y(1:3:end));
y=y(1:3:end);
disp(y);
disp(idx);
end

Adam Danz on 13 Dec 2019
I don't have a clear picture of the goal. Could you explain the bigger picture?
dpb on 13 Dec 2019
Indeed, the crystal ball is drawing a blank here. What is "the criteria" to which you refer? find simply returns all nonzero elements in the input argument; is that the criterion?
The element numbers removed would be those of idx if you were to subsequently remove those after the find operation, via y(idx)=[]; but those indices have any meaning only for the first pass and relative to the original input vector b; once removed the resulting y will be some other length and some of those indices will be out of range and none will refer to the same element in the resulting y
As Adam says, without some rationale, it's an impossible to answer question.
Pouya Afshin on 14 Dec 2019
Thanks for your response, Let me give you a general explanation of what I want to do. I am dealing with data compression in digital communication.
I am going to compress my data in encoder and give the index of those bits which are removed to the decoder in the receiver in order to estimate the original data in transmitter. What I wrote above was an example for this..
I defined a specific step for example 3 however i will change this in my algorithm later. It comes and keep every 3rd bits and remove the rest. for example
b=[2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 ];
for the first iteration my data in encoder will be
2 5 8 1 4 7 0 and other bits are removed. However in order to estimate the real data in decoder we need to give the information about those index which are removed in each iteration. for example here in first iteration these index are removed 2 3 5 6 8 9 11 12 ....
I just want to save these index in each iteration.
The criteria I was taling about was at the end after the iteration I don't want to get the length of y less than 4. it means it only remove bits as long as the length of y will be larger or equal to 4.
So what I need is, every iteration gives me new decremented y and also the index of those bits which are removed.
Is it possible?
I hope that my explanation was clear for you. If something was missing, please let me know to explain better.

Image Analyst on 13 Dec 2019
Is this what you want?
b = [2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1];
y = b;
% Find out which elements have a value of more than 4.
indexesToRemove = find(y>4);
y(indexesToRemove) = []; % Remove those indexes, or equivalently y = b(~indexesToRemove)

#### 1 Comment

Pouya Afshin on 14 Dec 2019
no this is not what i want, I explained what I want in previous response to Adam

dpb on 14 Dec 2019
That's simply the complement of the indices you saved...brute force is
>> ix=1:numel(b); ix(1:3:end)=[];
>> ix
ix =
2 3 5 6 8 9 11 12 14 15 17 18 20
>>
If you tell the decoding algorithm what decimation factor is, it can compute those on its own; doesn't need to be passed.

Adam Danz on 14 Dec 2019
Edited: Adam Danz on 17 Dec 2019
I'll admit to still not fully comprehending the problem though that fault may be on my end. From what I understand you want to recursively remove every n indices within a loop and you want to keep track of which indices are kept and tossed. I think the best way to manage that is by using a matrix of logical vectors where each column identifies the values of the vector b that you keep(1) or toss(0).
Here's a demo.
b=[2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 ];
n = 3; % keep every 'n' values
% compute number of columns
% This would be the number of iterations of your while-loop
% given n plus one column (you'll see why in the results section)
nCol = floor(log(numel(b))/log(n)) + 1;
% Initialize logical matrix
idx = false(numel(b),nCol);
% Identify selected data indices
rowIndices = n.^((1:nCol)-1);
for i = 1:nCol
idx(1:rowIndices(i):end,i) = true;
end
Results
For these data, idx is 20 x 3 (below).
Column 1 can be used when you want to select all of the values in b
b(idx(:,1))
Column 2 is every 3rd value in b
b(idx(:,2)) %keep
b(~idx(:,2)) %toss
Column 3 is every 3rd value of the values kept in the previous column, and so on....
1 1 1
1 0 0
1 0 0
1 1 0
1 0 0
1 0 0
1 1 0
1 0 0
1 0 0
1 1 1
1 0 0
1 0 0
1 1 0
1 0 0
1 0 0
1 1 0
1 0 0
1 0 0
1 1 1
1 0 0
Sorry if my interpretation is way off but if it's on target, this is a very easy way to select values in b without breaking apart your data.