티스토리 뷰

728x90

문제 링크

https://www.acmicpc.net/problem/1002


두 터렛의 위치 정보와 각 터렛에서 계산한 상대편 마린과의 거리가 주어질 때 마린이 있을 수 있는 위치를 출력하는 문제다.

마린이 있을 수 있는 위치는 '터렛 중심으로부터 거리가 일정한 점들의 집합'이다. 즉, 으로 볼 수 있다.


터렛이 두 대이므로 두 원끼리 겹치는 점의 개수가 답일 것이다.

원이 어떤 상황에서 어떻게 겹치는지 알기 위해 다음 6가지 케이스를 보면 된다.

  1) 어떤 원이 다른 원에 포함되지 않으면서, 두 원이 접하지 않을 때

  2) 외접할 때

  3) 두 점에서 만날 때

  4) 내접할 때

  5) 작은 원이 큰 원 내부에 있으면서, 두 원이 접하지 않을 때

  6) 두 원이 같은 원일 때


이제 주어진 원들이 어떤 상태인지 판별하면 된다. 하나씩 살펴보자.
두 원 사이의 거리를 dist, 큰 원의 반지름을 r1, 작은 원의 반지름을 r2라고 정의하겠다. 



dist<r1+r2 이다.

이 경우 마린은 하나인데 두 원이 겹치는 부분이 없으므로 답은 0이다.


dist=r1+r2 이다.

이 경우 한 점에서 만나므로 답은 1이다.




3), 4), 5)는 모두

distr1+r2이므로 반지름의 합으로 판단 할 수 없다.

따라서 r1r2값에 대해 생각해야 한다.

dist>r1r2 이다.

두 점에서 만나므로 답은 2이다.


dist=r1r2 이다.

한 점에서 만나므로 답은 1이다.


dist<r1r2 이다.

원이 만나지 않으므로 답은 0이다.

이 경우는 dist<r1+r2이지만 엄연히 다른 경우이므로 먼저 확인해준다.

이때 가능한 위치의 개수는 무한대이다.



위 설명을 바탕으로 그대로 코드로 옮기면 된다.



정답 코드

#include <iostream>
using namespace std;
int x, y, r1, x2, y2, r2;
int dist() {
return (x - x2)*(x - x2) + (y - y2)*(y - y2);
}
int sq(int x) {
return x * x;
}
int main() {
ios_base::sync_with_stdio(false);
cin.tie(0);
int t;
cin >> t;
while (t--) {
cin >> x >> y >> r1 >> x2 >> y2 >> r2;
if (r1 == r2 && x == x2 && y == y2)
cout << -1;
else if (dist() > sq(r1 + r2))
cout << 0;
else if (dist() == sq(r1 + r2))
cout << 1;
else if (dist() < sq(r1 + r2)) {
if (dist() > sq(r2 - r1))
cout << 2;
else if (dist() == sq(r2 - r1))
cout << 1;
else if (dist() < sq(r2 - r1))
cout << 0;
}
cout << '\n';
}
}
view raw 1002.cpp hosted with ❤ by GitHub


728x90

'알고리즘 > 문제 풀이' 카테고리의 다른 글

[BOJ] 백준 1004 어린 왕자  (0) 2018.06.28
[BOJ] 백준 1003 피보나치 함수  (0) 2018.06.28
[BOJ] 백준 2747 피보나치 수  (0) 2018.06.28
[BOJ] 백준 1001 A - B  (0) 2018.06.27
[BOJ] 백준 1000 A + B  (0) 2018.06.27
댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
«   2025/03   »
1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30 31
글 보관함