Трехмерная перпендикулярная точка на линии от трехмерной точки - PullRequest
10 голосов
/ 21 февраля 2012

Этот вопрос уже задавался ранее в отношении 2D.Этот вопрос распространяется на 3D.Как найти перпендикулярную точку пересечения на линии из точки в трехмерном пространстве?Если моя линия определяется точками (x1,y1,z1) & (x2,y2,z2) и у меня есть точка (x3,y3,z3) в пространстве.

Как найти перпендикулярное пересечение точки (x4, y4, z4) на линиииз (x3, y3, z3)?

Ответы [ 4 ]

10 голосов
/ 21 февраля 2012

Для начала вам очень нужна некоторая реализация класса Vector3, пишете ли вы свою собственную, находите где-нибудь автономную реализацию в Интернете или используете библиотеку, которая содержит такую, как XNA или Sharp3D.Math .

Обычно линии в трехмерном пространстве представлены не двумя точками, а параметрическими уравнениями и управляются векторами, а не скалярами.Ваше параметрическое уравнение будет иметь вид:

x = x1 + t(x2-x1), y = y1 + t(y2-y1), z = z1 + t(z2-z1)

Вектор u определяется коэффициентами t..

Вектор PQ определяется выбранной вами точкой Q минус точка P на линии.Можно выбрать любую точку на линии, поэтому проще всего использовать линию t = 0, которая упрощается до x1, y1 и z1.

Определение кратчайшего расстояния между точкой и линией в трехмерном пространстве выглядит следующим образом:

D = || PQ x и ||/ || u ||

Где x - оператор перекрестного произведения, а || ... || - величина содержащегося вектора.В зависимости от того, какую библиотеку вы выберете, ваш код может отличаться, но он должен быть очень похожим:

Vector3 u = new Vector3(x2 - x1, y2 - y1, z2 - z1);
Vector3 pq = new Vector3(x3 - x1, y3 - y1, z3 - z1);

float distance = Vector3.Cross(pq, u).Length / u.Length;

Редактировать : я только что понял, что вы хотите фактическую точку пересечения, а нерасстояние.Формула, чтобы найти фактическую точку немного отличается.Вам нужно использовать внутреннее пространство продукта, чтобы получить компонент u , перпендикулярный PQ .Для этого вам нужно найти компонент u в направлении PQ :

(( PQ · u) / || u || ^ 2) * u

Это дает нам компонент w1 , но мы хотим w2 , который является компонентом между Q и линией:

PQ = w1 + w2

w2 = PQ - w1

Оттуда мы берем w2 идобавьте его к точке Q , чтобы получить точку на линии, ближайшей к Q .В коде это будет:

Vector3 p1 = new Vector3(x1, y1, z1);
Vector3 p2 = new Vector3(x2, y2, z2);
Vector3 q = new Vector3(x3, y3, z3);

Vector3 u = p2 - p1;
Vector3 pq = q - p1;
Vector3 w2 = pq - Vector3.Multiply(u, Vector3.Dot(pq, u) / u.LengthSquared);

Vector3 point = q - w2;

Где point.X равно x4, point.Y равно y4 и point.Z равно z4.

2 голосов
/ 01 июля 2014

Мы также можем использовать метод треугольника AAS.

A - (x1,y1,z1), B - (x2,y2,z3) , C - (x3,y3,z3)

Нам нужно найти точку D на линии AB, которая перпендикулярна точке C

Теперь мыиметь Направленные векторы

VectorAC = normalize(A - C),
VectorCA = normalize(C - A),
VectorAB = normalize(A - B),

Давайте рассмотрим АЦП как треугольник

Точечный продукт дает угол между 2 векторами

AngleA = Angle Between VectorAC and vectorAB
AngleD = Angle Between VectorDC and vector DA, Always 90 deg, As VectorDC and DA are perpendicular to each other.
AngleC =  180 - (AngleA + AngleD), Angle between VectorCD and VectorCA.

Итак, теперь у нас есть 3 угла треугольника

Используйте метод треугольника AAS и найдите расстояние между A и D.

http://www.mathsisfun.com/algebra/trig-solving-aas-triangles.html

 D = (A + (VectorAB * Distance between A and D)).
2 голосов
/ 21 февраля 2012

На практике вы просите вычислить расстояние между точкой и линией, поэтому Length вектора от (x3,y3,z3) указывают на линию, которая ортогональна вектору. Если мы представляем линию как вектор, это означает, что скалярное произведение обоих векторов равно 0. (это просто для того, чтобы дать вам подсказку).

0 голосов
/ 29 мая 2015

Я сделал расчет для ответа, помеченного как Лучший ответ:
пусть alpha = [(x3-x1) (x2-x1) + (y3-y1) (y2-y1) + (z3-z1) (z2-z1)] / [(x2 -x1) (x2-x1) + (y2-y1) (y2-y1) + (z2-z1) (z2-z1)]
точка пересечения = (x1 + alpha * (x2-x1), y1 + alpha * (y2-y1), z1 + alpha * (z2-z1)).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...