πŸ“šSTUDY/Etc

이항 κ³„μˆ˜ λ‚΄ λ§˜λŒ€λ‘œ 정리(with μž¬κ·€)

ν•΄λŠ”μ„  2020. 2. 27. 18:42

0. μ΄ν•­κ³„μˆ˜λž€?  binomial coefficient?

주어진 크기의 (μˆœμ„œ μ—†λŠ”) μ‘°ν•©μ˜ κ°€μ§“μˆ˜. n개의 μ›μ†Œλ₯Ό κ°€μ§€λŠ” μ§‘ν•©μ—μ„œ 크기가 r 인 뢀뢄집합을 κ³ λ₯΄λŠ” 경우의 수.

 

 

보톡 μœ„μ˜ 식과 같이 κ³„μ‚°ν•œλ‹€.

 

1. μž¬κ·€λ‘œ λ³΄λŠ” μ΄ν•­κ³„μˆ˜

μ΄ν•­κ³„μˆ˜λŠ” μ ν™”μ‹μœΌλ‘œ ꡬ할 μˆ˜λ„ μžˆλ‹€. 

 

(파슀칼의 μ‚Όκ°ν˜•μ„ 같이 보면 μˆ˜μ‹μ„ μ΄ν•΄ν•˜κΈ° 쉽닀)

 

#include <stdio.h>

long long bc(int n, int c) {
	if (n == c || c == 0) return 1;
	else return bc(n - 1, c) + bc(n - 1, c - 1);
}

int main(void) {
	int n, c;
	scanf("%d %d", &n, &c);
	printf("%lld\n", bc(n, c));

}

μœ„μ˜ 식을 μž¬κ·€λ‘œ ν‘œν˜„ν–ˆλ‹€.

 

그런데 μ΄λ ‡κ²Œ 짜면 문제점이 μƒκΈ°λŠ”λ°, 쑰금만 큰 수λ₯Ό 넣어도 계산이 ν™•μ—°νžˆ λŠλ €μ§„λ‹€λŠ” 것이닀. μ™œλƒν•˜λ©΄, 이 경우 μ€‘λ³΅ν•΄μ„œ κ³„μ‚°ν•˜λŠ” 뢀뢄이 κΈ°ν•˜κΈ‰μˆ˜μ μœΌλ‘œ λŠ˜μ–΄λ‚œλ‹€. μ•„λž˜ 호좜 트리λ₯Ό 보자.

 

두 번 이상 κ³„μ‚°ν•˜λŠ” 뢀뢄을 νšŒμƒ‰κΉ”λ‘œ μΉ ν•΄ λ³΄μ•˜λ‹€. 그럼, 이런 쀑볡 계산을 μ—†μ• κΈ° μœ„ν•΄ 무엇을 ν•  수 μžˆμ„κΉŒ?

 

2. λ©”λͺ¨μ΄μ œμ΄μ…˜

κ²°κ΅­ μš”μ μ€ 계산을 ν•œ 번만 ν•˜λŠ” 것이닀. κ·Έλ ‡λ‹€λ©΄, ν•œ 번 κ³„μ‚°λœ κ²°κ³Ό 값을 μ–΄λ”˜κ°€μ— μ €μž₯해두고, λ‹€μ‹œ κ·Έ 값을 μ“΄λ‹€λ©΄ μ–΄λ–¨κΉŒ? 이λ₯Ό μœ„ν•œ 기법이 λ©”λͺ¨μ΄μ œμ΄μ…˜μ΄λ‹€.

 

μ•„λž˜λŠ” λ©”λͺ¨μ΄μ œμ΄μ…˜μ„ μ΄μš©ν•΄μ„œ μ§  μ΄ν•­κ³„μˆ˜ μ½”λ“œλ‹€.

long long memo[200][200] = { 0, };

long long bc_memo(int n, int r) {
	if (memo[n][r] > 0)return memo[n][r];

	if (n == r || r == 0) return memo[n][r] = 1;
	else return bc_memo(n - 1, r) + bc_memo(n - 1, r - 1);

}

int main(void) {
	int n, r;
	scanf("%d %d", &n, &r);
	printf("%lld\n", bc_memo(n, r));

}

와, λ©”λͺ¨μ΄μ œμ΄μ…˜μ„ μ‚¬μš©ν•˜μ§€ μ•Šμ•˜λ”λΌλ©΄ 20 C 10을 계산할 λ•Œ 호좜이 369511번 κ±Έλ¦¬μ§€λ§Œ, μœ„μ˜ μ½”λ“œλ₯Ό μ‚¬μš©ν•œλ‹€λ©΄ 201번으둜 획기적으둜 호좜 횟수λ₯Ό 쀄일 수 μžˆλ‹€.

 

 

 


reference

https://ko.wikipedia.org/wiki/%EC%9D%B4%ED%95%AD_%EA%B3%84%EC%88%98

문제둜 ν’€μ–΄λ³΄λŠ” μ•Œκ³ λ¦¬μ¦˜(ν™©μΈμš±, κΉ€μš©ν˜)