This question already has answers here:
Find point of intersection between two vectors in MATLAB
(4 answers)
Closed 5 years ago.
I have 2 lines coordinates (x1,y1 x2,y2 and x3,y3 x4,y4), how can I calculate the intersection coordinates without plotting them?
You could use the function polyxpoly for getting the intersection points.
See here for documentation and further information.
Here is a short example:
start1 = [1;1];
end1 = [3;3];
line1 = [start1, end1];
start2 = [1;3];
end2 = [2;1];
line2 = [start2,end2];
[xi, yi] = polyxpoly(line1(1,:), line1(2,:), line2(1,:), line2(2,:));
This will give you the intersection point xi and yi.
Note that this function is capable of a lot more than dealing with simple lines, such as boxes, intersection segments, etc.
The intersection point will be (x,y) = ((b1-b)/(1-a1), (a1*b-b1*a)/(a1-a))
where a = (y1-y2)/(x1-x2);
a1 = (y3-y4)/(x3-x4);
b = y1 - x1*(y1-y2)/(x1-x2);
b1 = y3 - x3*(y3-y4)/(x3-x4)
You can check the algebra by following these steps:
1) find the equation for the line passing by (x1,y1) and (x2,y2) and another equation for the line passing by the other two points;
2) force equality onto the two equations and you will have the intersection point
Related
This question already has answers here:
What is the advantage of linspace over the colon ":" operator?
(3 answers)
Closed 4 years ago.
I am wanting to do a very simple plot of a polynomial using the plot(x,y) function. Here is my full code
a = linspace(-3, 0.1, 3);
plot(a, a.^3 - 3*a - 2);
ax = gca;
c = ax.Color;
grid on;
Which outputs the following picture
Why doesn't the graph extend from -3 to 3 on the x-axis? Why does it stop just after $0$?
As the documentation states, in linspace(x1,x2,n) x1 is the begin value, x2 is the end value and n is the number of points. That's exacly what you see on your plot: 3 points: -3, 0.1 and one halfway (because of the linear spacing).
Since you want to have a particular spacing between your points, and not a certain number of points, I suggest you build your vector as:
a = -3:.1:3;
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 5 years ago.
Improve this question
Knowing center of the two rectangles and their angle by x axis (horizontal axis), how can one recognize if their intersection is zero or not in Matlab? Any answers containing this information is highly appreciated. Width and length of rectangles are also known
This is a programming problem if you want to solve it numerically. For exact solutions, you could use geometrical equations.
The first problem: defining a rectangle's corners from its width, height and centre:
C1 = [0, 0]; % Centre of rectangle 1 (x,y)
C2 = [1, 1]; % Centre of rectangle 2 (x,y)
W1 = 5; W2 = 3; % Widths of rectangles 1 and 2
H1 = 2; H2 = 3; % Heights of rectangles 1 and 2
% Define the corner points of the rectangles using the above
R1 = [C1(1) + [W1; W1; -W1; -W1]/2, C1(2) + [H1; -H1; -H1; H1]/2];
R2 = [C2(1) + [W2; W2; -W2; -W2]/2, C2(2) + [H2; -H2; -H2; H2]/2];
Next problem is to create many points which represent the edges of the rectangles. You could instead generate many points within the rectangles if you wanted to look at intersecting areas.
n = 1000; % Define some number of points to use
% Use interp1 to interpolate around the rectangles
R1points = interp1(1:5, [R1; R1(1,:)], linspace(1,5,n));
R2points = interp1(1:5, [R2; R2(1,:)], linspace(1,5,n));
Then rotate the rectangles:
a1 = deg2rad(0); a2 = deg2rad(30); % angles of rotation for rectangle 1 and 2 respectively
R1rotated(:,1) = (R1points(:,1)-C1(1))*cos(a1) - (R1points(:,2)-C1(2))*sin(a1) + C1(1);
R1rotated(:,2) = (R1points(:,1)-C1(1))*sin(a1) + (R1points(:,2)-C1(2))*cos(a1) + C1(2);
R2rotated(:,1) = (R2points(:,1)-C2(1))*cos(a2) - (R2points(:,2)-C2(2))*sin(a2) + C2(1);
R2rotated(:,2) = (R2points(:,1)-C2(1))*sin(a2) + (R2points(:,2)-C2(2))*cos(a2) + C2(2);
Finally, check intersection with inpolygon:
in1 = inpolygon(R1rotated(:,1), R1rotated(:,2), R2rotated(:,1), R2rotated(:,2));
in2 = inpolygon(R2rotated(:,1), R2rotated(:,2), R1rotated(:,1), R1rotated(:,2));
If nnz(in1)>0 or nnz(in2)>0 then you have an intersection! Visualise it using scatter:
hold on
scatter(R2rotated(:,1), R2rotated(:,2), '.b')
scatter(R2rotated(in2,1), R2rotated(in2,2), 'xc')
scatter(R1rotated(:,1), R1rotated(:,2), '.r')
scatter(R1rotated(in1,1), R1rotated(in1,2), 'xg')
Result:
I have two equations:
ellipseOne = '((x-1)^2)/6^2 + y^2/3^2 = 1';
and
ellipseTwo = '((x+2)^2)/2^2 + ((y-5)^2)/4^2 = 1';
and I plotted them:
ezplot(ellipseOne, [-10, 10, -10, 10])
hold on
ezplot(ellipseTwo, [-10, 10, -10, 10])
title('Ellipses')
hold off
Now I'm trying to find the intersection of the two ellipses. I tried:
intersection = solve(ellipseOne, ellipseTwo)
intersection.x
intersection.y
to find the points where they intersect, but MATLAB is giving me a matrix and an equation as an answer which I don't understand. Could anyone point me in the right direction to get the coordinates of intersection?
The solution is in symbolic form. The last step you need to take is to transform it into numeric. Simply convert the result using double. However, because this is a pair of quadratic equations, there are 4 possible solutions due to the sign ambiguity (i.e. +/-) and can possibly give imaginary roots. Therefore, isolate out the real solutions and what is left should be your answer.
Therefore:
% Your code
ellipseOne = '((x-1)^2)/6^2 + y^2/3^2 = 1';
ellipseTwo = '((x+2)^2)/2^2 + ((y-5)^2)/4^2 = 1';
intersection = solve(ellipseOne, ellipseTwo);
% Find the points of intersection
X = double(intersection.x);
Y = double(intersection.y);
mask = ~any(imag(X), 2) | ~any(imag(Y), 2);
X = X(mask); Y = Y(mask);
The first three lines of code are what you did. The next four lines extract out the roots in numeric form, then I create a logical mask that isolates out only the points that are real. This looks at the imaginary portion of both the X and Y coordinate of all of the roots and if there is such a component for any of the roots, we want to eliminate those. We finally remove the roots that are imaginary and we should be left with two real roots.
We thus get for our intersection points:
>> disp([X Y])
-3.3574 2.0623
-0.2886 2.9300
The first column is the X coordinate and the second column is the Y coordinate. This also seems to agree with the plot. I'll take your ellipse plotting code and also insert the intersection points as blue dots using the above solution:
ezplot(ellipseOne, [-10, 10, -10, 10])
hold on
ezplot(ellipseTwo, [-10, 10, -10, 10])
% New - place intersection points
plot(X, Y, 'b.');
title('Ellipses');
hold off;
This question already has an answer here:
Draw ellipse in MATLAB
(1 answer)
Closed 6 years ago.
Any ellipse can be uniquely defined by five parameters i.e. center x0 and y0, semi-major aixs length a, semi minor axis length b, and orientation angle theta. I have parameters x0, y0, a, b, and theta. How can I exactly draw the ellipse?
Some researches are necessary before to ask this kind of question. Mainly if the question was asked too much time.
You can do something like this :
Let (x1,y1) and (x2,y2) be the coordinates of the two vertices of the ellipse's major axis, and let e be its eccentricity.
a = 1/2*sqrt((x2-x1)^2+(y2-y1)^2);
b = a*sqrt(1-e^2);
t = linspace(0,2*pi);
X = a*cos(t);
Y = b*sin(t);
w = atan2(y2-y1,x2-x1);
x = (x1+x2)/2 + X*cos(w) - Y*sin(w);
y = (y1+y2)/2 + X*sin(w) + Y*cos(w):
plot(x,y,'y-')
axis equal
I don't have time to test it, but it should work.
Next time, please read this section : How do I ask a good question
I have a problem I've been trying to solve and I cannot come up with the answer. I have written a function in Matlab which, given two lat/lon points and two bearings, will return the two great circle points of intersection.
However, what I really need is the first great circle point of intersection along the two initial headings. I.e. if two airplanes begin at lat/lon points 1 and 2, with initial bearings of bearing1 and bearing2, which of the two great circle intersection points is the first one they encounter? There are many solutions (using haversine) which will give me the closer of the two points, but I don't actually care about which is closer, I care about which I will encounter first given specific start points and headings. There are many cases where the closer of the two intersections is actually the second intersection encountered.
Now, I realize I could do this with lots of conditional statements for handling the different cases, but I figure there's got to be a way to handle it with regard to the order I take all my cross products (function code given below), but I simply can't come up with the right solution! I should also mention that this function is going to be used in a large computationally intensive model, and so I'm thinking the solution to this problem needs to be rather elegant/speedy. Can anyone help me with this problem?
The following is not my function code (I can't list that here), but it is the pseudo code that my function was based off of:
%Given inputs of lat1,lon1,Bearing1,lat2,lon2,Bearing2:
%Calculate arbitrary secondary point along same initial bearing from first
%point
dAngle = 45;
lat3 = asind( sind(lat1)*cosd(dAngle) + cosd(lat1)*sind(dAngle)*cosd(Bearing1));
lon3 = lon1 + atan2( sind(Bearing1)*sind(dAngle)*cosd(lat1), cosd(dAngle)-sind(lat1)*sind(lat3) )*180/pi;
lat4 = asind( sind(lat2)*cosd(dAngle) + cosd(lat2)*sind(dAngle)*cosd(Bearing2));
lon4 = lon2 + atan2( sind(Bearing2)*sind(dAngle)*cosd(lat2), cosd(dAngle)-sind(lat2)*sind(lat4) )*180/pi;
%% Calculate unit vectors
% We now have two points defining each of the two great circles. We need
% to calculate unit vectors from the center of the Earth to each of these
% points
[Uvec1(1),Uvec1(2),Uvec1(3)] = sph2cart(lon1*pi/180,lat1*pi/180,1);
[Uvec2(1),Uvec2(2),Uvec2(3)] = sph2cart(lon2*pi/180,lat2*pi/180,1);
[Uvec3(1),Uvec3(2),Uvec3(3)] = sph2cart(lon3*pi/180,lat3*pi/180,1);
[Uvec4(1),Uvec4(2),Uvec4(3)] = sph2cart(lon4*pi/180,lat4*pi/180,1);
%% Cross product
%Need to calculate the the "plane normals" for each of the two great
%circles
N1 = cross(Uvec1,Uvec3);
N2 = cross(Uvec2,Uvec4);
%% Plane of intersecting line
%With two plane normals, the cross prodcut defines their intersecting line
L = cross(N1,N2);
L = L./norm(L);
L2 = -L;
L2 = L2./norm(L2);
%% Convert normalized intersection line to geodetic coordinates
[lonRad,latRad,~]=cart2sph(L(1),L(2),L(3));
lonDeg = lonRad*180/pi;
latDeg = latRad*180/pi;
[lonRad,latRad,~]=cart2sph(L2(1),L2(2),L2(3));
lonDeg2 = lonRad*180/pi;
latDeg2 = latRad*180/pi;
UPDATE: A user on the Mathworks forums pointed this out:
Actually they might each reach a different point. I might have misunderstood the question, but the way you worded it suggests that both trajectories will converge towards the same point, which is not true. If you image the first point being a little after one intersection and the second point being a little after the other intersection, you have a situation were each "plane" will travel towards the intersection that was the closest to the other plane at the beginning.
I didn't think about this. It is actually very possible that each of the planes intersects a different great circle intersection first. Which just made things much more complicated...
Presumably you have a velocity vector for the direction of the plane (the direction in which you want to look for your first intersection - the "bearing vector on the surface of the earth"). You didn't actually specify this. Let us call it v.
You also have the cartesian coordinates of two points, P1 and P2, as well as the initial position of the plane, P0. Each is assumed to be already on the unit sphere (length = 1).
Now we want to know which is the shorter distance - to P1, or P2 - so we need to know the angle "as seen from the direction of the normal vector". For this we need both the sin and the cos - then we can find the angle using atan2. We obtain sin from the cross product (remember all vectors were normalized), and cos from the dot product. To get the sin "as seen from the right direction", we take dot product with the normal vector.
Here is a piece of code that puts it all together - I am using very simple coordinates for the points and direction vector so I can confirm in my head that this gives the correct answer:
% sample points of P0...P2 and v
P0 = [1 0 0];
P1 = [0 1 0];
P2 = [0 -1 0];
v = [0 1 0];
% compute the "start direction normal":
n0 = cross(P0, v);
n0 = n0 / norm( n0 ); % unit vector
% compute cross and dot products:
cr01 = cross(P0, P1);
cr02 = cross(P0, P2);
cos01 = dot(P0, P1);
cos02 = dot(P0, P2);
% to get sin with correct sign, take dot product with direction normal:
sin01 = dot(cr01, n0);
sin02 = dot(cr02, n0);
% note - since P0 P1 and P2 are all in the same plane
% cr02 and cr02 are either pointing in the same direction as n0
% or the opposite direction. In the latter case we get a sign flip for the sin
% in the former case this does nothing
% Now get the angle, mapped from 0 to 2 pi:
ang1 = mod(atan2(sin01, cos01), 2*pi);
ang2 = mod(atan2(sin02, cos02), 2*pi);
if( ang1 < ang2 )
fprintf(1,'point 1 is reached first\n');
% point 1 is the first one reached
else
fprintf(1,'point 2 is reached first\n');
% point 2 is the first
end
When you change the direction of the velocity vector (pointing towards P2 instead of P1), the program correctly tells you "point 2 is reached first".
Let me know if this works for you!