Algorithm/λ¬Έμ œν’€μ΄

[λ°±μ€€] 2294번 - 동전 2 (C++)

moaoh 2023. 8. 26. 15:16

 

2294번: 동전 2

첫째 쀄에 n, kκ°€ μ£Όμ–΄μ§„λ‹€. (1 ≤ n ≤ 100, 1 ≤ k ≤ 10,000) λ‹€μŒ n개의 μ€„μ—λŠ” 각각의 λ™μ „μ˜ κ°€μΉ˜κ°€ μ£Όμ–΄μ§„λ‹€. λ™μ „μ˜ κ°€μΉ˜λŠ” 100,000보닀 μž‘κ±°λ‚˜ 같은 μžμ—°μˆ˜μ΄λ‹€. κ°€μΉ˜κ°€ 같은 동전이 μ—¬λŸ¬ 번 μ£Όμ–΄

www.acmicpc.net

문제

nκ°€μ§€ μ’…λ₯˜μ˜ 동전이 μžˆλ‹€. 이 동전듀을 μ λ‹Ήνžˆ μ‚¬μš©ν•΄μ„œ, κ·Έ κ°€μΉ˜μ˜ 합이 k원이 λ˜λ„λ‘ ν•˜κ³  μ‹Άλ‹€. κ·ΈλŸ¬λ©΄μ„œ λ™μ „μ˜ κ°œμˆ˜κ°€ μ΅œμ†Œκ°€ λ˜λ„λ‘ ν•˜λ €κ³  ν•œλ‹€. 각각의 동전은 λͺ‡ κ°œλΌλ„ μ‚¬μš©ν•  수 μžˆλ‹€.

μ‚¬μš©ν•œ λ™μ „μ˜ ꡬ성이 같은데, μˆœμ„œλ§Œ λ‹€λ₯Έ 것은 같은 κ²½μš°μ΄λ‹€.

 

 

 

μž…λ ₯

첫째 쀄에 n, kκ°€ μ£Όμ–΄μ§„λ‹€. (1 ≤ n ≤ 100, 1 ≤ k ≤ 10,000) λ‹€μŒ n개의 μ€„μ—λŠ” 각각의 λ™μ „μ˜ κ°€μΉ˜κ°€ μ£Όμ–΄μ§„λ‹€. λ™μ „μ˜ κ°€μΉ˜λŠ” 100,000보닀 μž‘κ±°λ‚˜ 같은 μžμ—°μˆ˜μ΄λ‹€. κ°€μΉ˜κ°€ 같은 동전이 μ—¬λŸ¬ 번 μ£Όμ–΄μ§ˆ μˆ˜λ„ μžˆλ‹€.

 

 

 

좜λ ₯

첫째 쀄에 μ‚¬μš©ν•œ λ™μ „μ˜ μ΅œμ†Œ 개수λ₯Ό 좜λ ₯ν•œλ‹€. λΆˆκ°€λŠ₯ν•œ κ²½μš°μ—λŠ” -1을 좜λ ₯ν•œλ‹€.

 

풀이과정

λ¬Έμ œμ—μ„œ μš”κ΅¬ν•˜λŠ” 사항은 kλΌλŠ” 값을 λ§Œλ“€κΈ°μœ„ν•΄μ„œ ν•„μš”ν•œ 동전에 μ΅œμ†Œκ°œμˆ˜λ₯Ό κ΅¬ν•˜λΌ λΌλŠ” λ¬Έμ œμ˜€μ—ˆλ‹€.

문제의 μœ ν˜•μžμ²΄κ°€ 전에 ν’€μ—ˆλ˜ 동전 1에 λΉ„ν•΄μ„œλŠ” λ‚˜λ¦„ μΉœμˆ™ν–ˆλ˜ λ¬Έμ œμ˜€μ–΄μ„œ μ‰½κ²Œ μ ‘κ·Όν•  수 μžˆμ—ˆλ˜ κ±° κ°™λ‹€.

 

λ¬Έμ œμ—μ„œ μš”κ΅¬ν•˜λŠ” kλ₯Ό λ§Œλ“€κΈ° μœ„ν•œ λ™μ „μ˜ μ΅œμ†Œκ°œμˆ˜λ₯Ό κ΅¬ν•˜λŠ” 방법은 

dp[k] = (dp[k - (λ™μ „μ˜ μ’…λ₯˜)] + 1) 쀑 μ΅œμ†Œ κ°’μ΄μ—ˆλ‹€. 

dp[k - (λ™μ „μ˜ μ’…λ₯˜)]λΌλŠ” 값은 k보닀 μž‘μ€ 값듀을 κ΅¬ν•˜λŠ” 동전에 μ΅œμ†Œκ°œμˆ˜λ₯Ό κ΅¬ν•΄μ˜¨ 과정이고,

dp[k - (λ™μ „μ˜ μ’…λ₯˜)]λŠ” λ‹€μ–‘ν•œ λ™μ „μ˜ μ’…λ₯˜ μ€‘μ—μ„œλ„ κ·Έ 쀑에 κ°€μž₯ μž‘μ€ 값이 μžˆμ„ κ²ƒμ΄κΈ°λ•Œλ¬Έμ— 비ꡐλ₯Ό ν•΄κ°€λ©΄μ„œ κ°€μž₯ μž‘μ€ dp[k]λΌλŠ” 값을 κ΅¬ν•˜λŠ” λ°©μ‹μœΌλ‘œ μ½”λ“œν’€μ΄λ₯Ό μ§„ν–‰ν•˜μ˜€λ‹€.

code

#include <iostream>

int		coin[101];
int		dp[10001];

int		main(void)
{
	int n, k, temp;

	std::cin >> n >> k;
	for (int i = 0; i < n; i++) {
		std::cin >> coin[i];
	}
	for (int i = 1; i <= k; i++) {
		dp[i] = 10001;
		for (int j = 0; j < n; j++) {
			if (i == coin[j])
				dp[i] = 1;
			else if (0 < i - coin[j] && dp[i - coin[j]] + 1 < dp[i]) {
				dp[i] = dp[i - coin[j]] + 1;
			}
		}
	}
	if (dp[k] == 10001) std::cout << "-1";
	else std::cout << dp[k];

	return (0);
}

 

ν›„κΈ°

μΉœμˆ™ν–ˆλ˜ μœ ν˜•μ΄μ—ˆμ–΄μ„œ 점화식접근에 크게 μ˜€λž˜κ±Έλ¦¬μ§€λŠ” μ•Šμ•˜λ˜ κ±° κ°™λ‹€.