※ 글쓴이는 취미로 코딩을 익혀보는 사람이라 정확하지 않은 내용을 담고 있을 수 있다 ※

 

이번에 볼 문제는 백준 2700번 문제인 볼록 격자 다각형의 내부점이다.
문제는 아래 링크를 확인하자.

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

 

2700번: 볼록 격자 다각형의 내부점

첫 줄에는 수평선의 개수를 출력한다. 만약, 수평선이 하나 이상 있다면, 수평선의 y 좌표 값을 한 줄에 하나씩 출력한다. 이때 y좌표 내림차순으로 출력한다. 각각의 y좌표 값 뒤에 공백을 사이

www.acmicpc.net

볼록다각형의 내부에 점이 있는지 확인하는 가장 쉬운 방법은 다각형을 일정한 방향으로 돌면서 각 변과 점 사이의 CCW의 값을 확인하는 것이다. 점이 다각형의 내부에 있다면 CCW의 값은 전부 1로 통일되어있거나 -1로 통일되어있을 것이라는 점을 관찰하자.

 

주어지는 좌표의 범위가 매우 작다는 점을 이용해서, 각 테스트케이스마다 x와 y가 각각 -30 이상 30 이하인 모든 점(61*61=3721개)에 대해 각 점이 주어진 다각형의 내부에 있는지를 테스트하는 것으로 문제를 해결할 수 있다.

 

아래는 제출한 소스코드이다.

#include <iostream>
#include <vector>
using namespace std;

int N;
pair<int, int> points[51];

int CCW(pair<int, int>& p1, pair<int, int>& p2, pair<int, int>& p3) {
	int ccw = (p2.first - p1.first) * (p3.second - p1.second) - (p2.second - p1.second) * (p3.first - p1.first);
	if (ccw > 0) return 1;
	else return 0;
}

void solve() {
	vector<int> ans[61];
	int anscnt = 0;
	cin >> N;
	for (int i = 0; i < N; i++) cin >> points[i].first >> points[i].second;
	points[N] = points[0];

	for (int y = -29; y < 30; y++) {
		for (int x = -29; x < 30; x++) {
			pair<int, int> cur = make_pair(x, y);
			int cnt = 0;
			for (int i = 0; i < N; i++) {
				cnt += CCW(points[i], cur, points[i + 1]);
			}
			if (cnt < N) continue;
			ans[y + 30].emplace_back(x);
		}
	}
	
	for (int y = 1; y < 60; y++) {
		if (!ans[y].empty()) anscnt++;
	}
	cout << anscnt << '\n';

	for (int y = 59; y > 0; y--) {
		if (!ans[y].empty()) {
			cout << y - 30 << ' ' << ans[y].front() << ' ' << ans[y].back() << '\n';
		}
	}
}

int main() {
	ios::sync_with_stdio(0);
	cin.tie(0);

	int T; cin >> T;
	while (T--) solve();
}
728x90

'BOJ' 카테고리의 다른 글

[BOJ 2693 // C++] N번째 큰 수  (0) 2023.04.25
[BOJ 2701 // C++] 육각 퍼즐  (0) 2023.04.24
[BOJ 2698 // C++] 인접한 비트의 개수  (0) 2023.04.22
[BOJ 2697 // C++] 다음수 구하기  (0) 2023.04.21
[BOJ 2694 // C++] 합이 같은 구간  (0) 2023.04.20

+ Recent posts