Я нарисовал линию между двумя точками A (x, y) --- B (x, y) Теперь у меня есть третья точка C (x, y). Я хочу знать, что если C лежит на линии, которая тянется между A и B. Я хочу сделать это на языке Java. Я нашел пару ответов, подобных этому. Но у всех есть проблемы, и никто не идеален.
Проверить, что точка (x, y) находится между двумя точками, нарисованными по прямой
Ответ 1
if (distance(A, C) + distance(B, C) == distance(A, B))
return true; // C is on the line.
return false; // C is not on the line.
или просто:
return distance(A, C) + distance(B, C) == distance(A, B);
Как это работает, довольно просто. Если C лежит на строке AB
, вы получите следующий сценарий:
A-C------B
и, независимо от того, где он лежит на этой строке, dist(AC) + dist(CB) == dist(AB)
. Для любого другого случая у вас есть треугольник некоторого описания и "dist (AC) + dist (CB) > dist (AB)":
A-----B
\ /
\ /
C
Фактически, это даже работает, если C лежит на экстраполированной строке:
C---A-------B
при условии, что расстояния сохраняются без знака. Расстояние dist(AB)
можно рассчитать как:
___________________________
/ 2 2
V (A.x - B.x) + (A.y - B.y)
Имейте в виду присущие ограничения (ограниченную точность) операций с плавающей запятой. Возможно, вам понадобится выбрать тест "достаточно близко" (скажем, менее одной части на миллион ошибок), чтобы обеспечить правильное функционирование равенства.
Ответ 2
ВНИМАНИЕ! Math-только!
Вы можете попробовать эту формулу. Поместите ваши координаты A(x1, y1)
и B(x2, y2)
в формулу, тогда вы получите что-то вроде
y = k*x + b; // k and b - numbers
Тогда любая точка, которая удовлетворяет этому уравнению, будет лежать на вашей линии.
Чтобы проверить, что C(x, y)
находится между A(x1, y1)
и B(x2, y2)
, проверьте следующее: (x1<x<x2 && y1<y<y2) || (x1>x>x2 && y1>y>y2)
.
Пример
A(2,3) B(6,5)
Уравнение прямой:
(y - 3)/(5 - 3) = (x - 2)/(6 - 2)
(y - 3)/2 = (x - 2)/4
4*(y - 3) = 2*(x - 2)
4y - 12 = 2x - 4
4y = 2x + 8
y = 1/2 * x + 2; // equation of line. k = 1/2, b = 2;
Проверить, находится ли C(4,4)
на этой строке.
2<4<6 & 3<4<5 // C between A and B
Теперь поместите координаты C в уравнение:
4 = 1/2 * 4 + 2
4 = 2 + 2 // equal, C is on line AB
PS:, как писал @paxdiablo, вам нужно проверить, горизонтальна или вертикальна линия перед вычислением. Просто проверьте
y1 == y2 || x1 == x2
Ответ 3
Я считаю, что самый простой
// is BC inline with AC or visa-versa
public static boolean inLine(Point A, Point B, Point C) {
// if AC is horizontal
if (A.x == C.x) return B.x == C.x;
// if AC is vertical.
if (A.y == C.y) return B.y == C.y;
// match the gradients
return (A.x - C.x)*(A.y - C.y) == (C.x - B.x)*(C.y - B.y);
}
Вы можете рассчитать градиент, взяв разницу в значениях x, деленных на разницу в значениях y.
Примечание: есть другой тест, чтобы увидеть, появляется ли C на линии между A и B, если вы нарисуете его на экране. Математика предполагает, что A, B, C - бесконечно малые точки. На самом деле очень маленькая с ошибкой представления.
Ответ 4
Вышеупомянутые ответы излишне сложны. Простейшим является следующее.
-
if (x-x1)/(x2-x1) = (y-y1)/(y2-y1) = alpha (константа), то точка C (x, y) будет лежать на между пунктами 1 и 2.
-
Если альфа- 0.0, то C является внешним по отношению к точке 1.
- Если alpha > 1.0, то C является внешним по отношению к точке 2.
- Наконец, если alpha = [0,1.0], то C является внутренним к 1 и 2.
Надеюсь, что этот ответ поможет.