Olbert Daemmerer
Olbert Daemmerer

Reputation: 141

How to remove coordinate specific entries from a matrix?

I'm having trouble to implement this (seemingly) simple task in Octave/Matlab.

I want to remove specific entries of a set of 2dimensional data. I have sample data (points of x and y coordinates) which contain specific areas that should not be further processed. I want to delete these areas from my sample data.

Here is an example for further understanding what I want to achieve. I would like to have:

B = A except the data in the red rectangle

Code Sample:

x = 0:pi/64:4*pi;
y = sin(x);

A = [x; y];

% Boundaries of the data that should be deleted
x1 = 4;
x2 = 6;
y1 = -1;
y2 = -0.5;

figure;
hold on;
plot(A(1,:),A(2,:),'bo');
plot([x1 x2 x2 x1 x1],[y1 y1 y2 y2 y1],'r-');

I know how to select the data within the red rectangle, which can be done with this command:

indices = find(A(1,:)>x1 & A(1,:)<x2 & A(2,:)>y1 & A(2,:)<y2);
B(1,:) = A(1,indices);
B(2,:) = A(2,indices);
plot(B(1,:),B(2,:),'g-x');

But I need the opposite: Select the data outside the red rectangle.

Any help is appreciated.

Upvotes: 1

Views: 481

Answers (2)

Georg W.
Georg W.

Reputation: 1356

Use logical arrays to select data

A very handy way of managing selections is the use of logical arrays. This is faster than using indices and allows the easy inversion of a selection as well as the combination of multiple selections. Here comes the modified selection function:
sel = A(1,:)>x1 & A(1,:)<x2 & A(2,:)>y1 & A(2,:)<y2
The result is a logical array that is a very memory efficient and fast representation of your information.

See figure for graphical representation of output.

Code Example

x = 0:pi/64:4*pi;
y = sin(x);
% Combine data: This is actually not necessary
% and makes the method more complicated. If you can stay with x and y
% arrays formulation becomes shorter
A = [x; y];
    
% Boundaries of the data that should be deleted
x1 = 4;
x2 = 6;
y1 = -1;
y2 = -0.5;

% Select interesting data
sel = A(1,:)>x1 & A(1,:)<x2 & A(2,:)>y1 & A(2,:)<y2;
% easily invert selection with the rest of data
invsel = ~sel;

% Get selected data to a new array
B1 = A(:,sel);
B2 = A(:,invsel);

% Display your data
figure;
hold on;
plot(B1(1,:),B1(2,:),'bo');
plot(B2(1,:),B2(2,:),'rx');

% Plot selection box in green
plot([x1 x2 x2 x1 x1],[y1 y1 y2 y2 y1],'g-');

Graphical Result

Graphical result of above sample script on selecting data

Upvotes: 0

JMikes
JMikes

Reputation: 662

Invert all of the operators in your statement defining indices (i.e. > becomes < and vice-versa, AND[ & ] becomes OR[ | ]).

indices2 = find(A(1,:)<x1 | A(1,:)>x2 | A(2,:)<y1 | A(2,:)>y2);
B=A(:,indices2);
plot(B(1,:),B(2,:),'g-x');

Upvotes: 1

Related Questions