Computer >> 컴퓨터 >  >> 프로그래밍 >> C++

C++로 2D 평면에서 점에서 직선까지의 수선의 발 구하기


2차원 평면 위의 한 점 P와 직선의 방정식이 주어졌을 때, 점 P에서 그 직선으로 내린 수선의 발(foot of perpendicular)의 좌표를 구하는 것이 이 글의 목표입니다. 기하학적 개념을 간단한 대수 공식으로 바꾸면 코드 몇 줄만으로도 손쉽게 해를 구할 수 있습니다.

수학적 접근 방법

주어진 직선의 방정식은 다음과 같습니다.

ax + by + c = 0

점 P(x1, y1)를 지나면서 위 직선에 수직인 직선은 다음 형태의 방정식을 갖습니다.

ay − bx + d = 0

이 수직선이 원래의 직선과 만나는 점을 Q(x2, y2)라 하겠습니다. 점 P의 좌표를 수직선의 방정식에 대입하면 상수 d를 구할 수 있습니다.

ay1 − bx1 + d = 0, 따라서 d = bx1 − ay1

점 Q는 주어진 직선과 점 P를 지나는 수직선의 교점이므로, 두 방정식을 연립하여 풀면 됩니다.

ax + by + c = 0
ay − bx + (bx1 − ay1) = 0

a, b, c, d의 값이 모두 알려져 있으므로, 다음 공식을 이용해 수선의 발의 좌표를 곧바로 계산할 수 있습니다.

$$\frac{x-x_{1}}{a}=\frac{y-y_{1}}{b}=\frac{-(ax_{1}+by_{1}+c)}{a^{2}+b^{2}}$$

C++ 구현 예제

#include<iostream>
using namespace std;

void getFootCoordinate(double a, double b, double c, double x1, double y1) {
    double p = -1 * (a * x1 + b * y1 + c) / (a * a + b * b);
    double x = p * a + x1;
    double y = p * b + y1;
    cout << "(" << x << ", " << y << ")";
}

int main() {
    double a = 0.0;
    double b = 1.0;
    double c = -2;
    double x1 = 3.0;
    double y1 = 3.0;
    cout << "좌표는: ";
    getFootCoordinate(a, b, c, x1, y1);
}

실행 결과

좌표는: (3, 2)

코드 설명

함수 getFootCoordinate는 앞서 유도한 공식을 그대로 코드로 옮긴 것입니다. 먼저 p = −(ax₁ + by₁ + c) / (a² + b²) 값을 계산한 뒤, 수선의 발의 좌표를 (x₁ + p·a, y₁ + p·b)로 구합니다.

예제에서는 a = 0, b = 1, c = −2이므로 직선은 y = 2, 즉 x축에 평행한 수평선입니다. 점 P(3, 3)에서 이 직선에 수선을 내리면 x좌표는 그대로 유지된 채 y좌표만 2가 되므로 수선의 발은 (3, 2)가 되며, 실행 결과 역시 이와 일치합니다.

이 방법은 시간 복잡도 O(1)로 상수 시간 안에 결과를 얻을 수 있으며, a와 b가 동시에 0이 아닌 한 어떤 직선에 대해서도 정확하게 동작합니다.