Лучший способ найти точку на окружности, ближайшей к данной точке - PullRequest
35 голосов
/ 19 ноября 2008

Учитывая точку (pX, pY) и окружность с известным центром (cX, cY) и радиусом (r), какой кратчайший объем кода вы можете придумать, чтобы найти точку на окружности, ближайшей к (pX, pY)?

У меня есть некоторый код, работающий, но он включает преобразование круга в уравнение вида (x - cX) ^ 2 + (y - cY) ^ 2 = r ^ 2 (где r - радиус) и используя уравнение линии от точки (pX, pY) до (cX, cY), чтобы создать квадратное уравнение, которое необходимо решить.

Как только я исправлю ошибки, это сработает, но, похоже, такое неумелое решение.

Ответы [ 8 ]

61 голосов
/ 19 ноября 2008

, где P - точка, C - центр, а R - радиус на подходящем "математическом" языке:

V = (P - C); Answer = C + V / |V| * R;

где | V | длина V.

ОК, ОК

double vX = pX - cX;
double vY = pY - cY;
double magV = sqrt(vX*vX + vY*vY);
double aX = cX + vX / magV * R;
double aY = cY + vY / magV * R;

легко расширить до> 2 размеров.

8 голосов
/ 19 ноября 2008

Я бы сделал линию от центра до точки и вычислил, где этот график пересекает окружность. Думаю, это не так сложно

3 голосов
/ 19 ноября 2008

Сначала решите это математически, а затем переведите в код. Помните, что самая короткая линия между точкой и краем круга также пройдет через ее центр (как указано @litb).

2 голосов
/ 31 августа 2012
  1. Самая короткая точка расстояния лежит на пересечении окружности и линии, проходящей через центр и точку входа. Также центральные, входные и выходные точки лежат на прямой линии

  2. пусть центр будет (xc, yc), а самая короткая точка на входе (xi, yi) будет (x, y) sqrt ((xc-x) ^ 2 + (yc-y) ^ 2) = r

  3. , так как центр, точки входа и выхода лежат на прямой линии, наклон рассчитывается между любой из этих двух пунктов должен быть одинаковым.

(yc-yi) / (xc-xi) = (y-yc) / (x-xc)

4. Решающие уравнения 2 и 3 должны дать нам самую короткую точку.

1 голос
/ 19 ноября 2008

Простой способ думать об этом с точки зрения картинки и легко превратить в код: возьмите вектор (pX - cX, pY - cY) от центра к точке. Разделите на его длину sqrt (бла-бла-бла), умножьте на радиус. Добавьте это к (cX, cY).

1 голос
/ 19 ноября 2008

Вы попросили самый короткий код, так что вот оно. В четыре строки это можно сделать, хотя есть еще квадратичный. Я считал, что точка находится за пределами круга. Я не учел, что произойдет, если точка находится прямо над или под центром круга, то есть cX = pX.

m=(cY-pY)/(cX-pX);  //slope
b=cY-m*cX;  //or Py-m*Px.  Now you have a line in the form y=m*x+b
X=(  (2mcY)*((-2*m*cY)^2-4*(cY^2+cX^2-b^2-2*b*cY-r^2)*(-1-m^2))^(1/2)  )/(2*(cY^2+cX^2-b^2-2*bc*Y-r^2));
Y=mX+b;

1] Получите уравнение для линии, соединяющей точку и центр окружности.

2] Двигайтесь вдоль линии на расстоянии одного радиуса от центра, чтобы найти точку на окружности. То есть: радиус = a ^ 2 + b ^ 2, который: r = ((cY-Y) + (cX-X)) ^ (1/2)

3] Решить квадратично. X = quadratic_solver (r = ((cY-Y) + (cX-X)) ^ (1/2), X), который, если вы подставите в Y = m * X + b, вы получите этот ад выше.

4] X и Y - ваши результаты по кругу.

Я вполне уверен, что где-то допустил ошибку, пожалуйста, оставьте комментарий, если кто-нибудь что-то найдет. Конечно, это вырожденный, один ответ наиболее далек от вашей точки зрения, а другой - ближайший.

1 голос
/ 19 ноября 2008

Относитесь к центру циркуляра как к источнику, преобразуйте координаты (pX, pY) в полярные координаты, (theta, r ') замените r' на исходный кружок r и преобразуйте обратно в декартову координату -координаты (и с учетом происхождения).

1 голос
/ 19 ноября 2008

Функции триггера, умножьте на r и добавьте pX или pY в зависимости от ситуации.

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