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

 

이번에 볼 문제는 백준 21213번 문제인 Mentors이다.
문제는 아래 링크를 확인하자.

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

 

21213번: Mentors

The node with label $R = 2$ is a leaf in exactly $3$ of five trees listed below, and thus there are $3$ trees that match Mr. Pickles' constraints. The only meaningful feature of our trees is parenthood, which represents mentorship relations, and thus there

www.acmicpc.net

노드를 K개 사용했을 때, K와 R의 대소에 따라 "자식을 추가로 2개 달 수 있는 노드"의 개수를 X로 고정하면 "자식을 추가로 1개 달 수 있는 노드"의 개수와 "이미 자식이 두개인 노드"의 개수가 정해진다는 것을 관찰할 수 있다.

 

이를 이용하여 dp[K][X]를 점화식을 이용하여 계산해내면 O(N^2)에 문제를 해결할 수 있다.

 

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

#include <iostream>
using namespace std;
typedef long long ll;

ll R, N, MOD;
ll dp[2022][1012];

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

	cin >> R >> N >> MOD;
	R = N - R + 1;
	if (R == 1) {
		if (N == 1) cout << 1 % MOD;
		else cout << 0;

		return 0;
	}
	dp[1][1] = 1;
	for (int r = 2; r < R; r++) {
		for (ll x = 1, y = r - 1; y >= 0; x++, y -= 2) {
			dp[r][x] = (dp[r - 1][x - 1] * (y + 1) + dp[r - 1][x] * x) % MOD;
		}
	}
	for (int r = R; r <= R; r++) {
		for (ll x = 0, y = r - 1; y >= 0; x++, y -= 2) {
			dp[r][x] = (dp[r - 1][x] * (y + 1) + dp[r - 1][x + 1] * (x + 1)) % MOD;
		}
	}
	for (int r = R + 1; r <= N; r++) {
		for (ll x = 1, y = r - 3; y >= 0; x++, y -= 2) {
			dp[r][x] = (dp[r - 1][x - 1] * (y + 1) + dp[r - 1][x] * x) % MOD;
		}
	}

	ll ans = 0;
	for (ll x = 0, y = N - 1; y >= 0; x++, y -= 2) {
		ans += dp[N][x];
	}

	cout << ans % MOD;
}

Changelog

2022-05-08: 어색한 문장 수정

728x90

'BOJ' 카테고리의 다른 글

[BOJ 2251 // C++] 물통  (0) 2022.05.06
[BOJ 15967 // C++] 에바쿰  (0) 2022.05.05
[BOJ 18405 // C++] 경쟁적 전염  (0) 2022.05.03
[BOJ 24933 // C++] Quadratic Dissonance  (0) 2022.05.02
[BOJ 25001 // C++] Pen  (0) 2022.05.01

+ Recent posts