본문 바로가기
PS

[BAEKJOON] 2011 암호코드 (C++)

by bin1225 2023. 7. 11.

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

 

2011번: 암호코드

나올 수 있는 해석의 가짓수를 구하시오. 정답이 매우 클 수 있으므로, 1000000으로 나눈 나머지를 출력한다. 암호가 잘못되어 암호를 해석할 수 없는 경우에는 0을 출력한다.

www.acmicpc.net

 

문제

문제는 숫자로 암호화된 문자열을 다시 문자형식으로 바꿀 때 가능한 경우의 수를 구하는 문제이다.

일반적인 DP냄새가 나는 문제

 

얼마전 스터디에서 https://www.acmicpc.net/problem/2302 문제를 풀었는데, DP점화식을 구성하는 것이 비슷하다.

 

풀이

숫자로 암호화된 문자열을 문자로 바꾸는 경우는 두가지이다.

1. 숫자 하나만 보고 문자로 변환

2. 숫자 두개를 묶어서 문자로 변환

 

즉 두개를 묶을 수 있다면, 두개를 묶는 조합의 수가 총 몇개나 가능한지를 확인하는 문제라는 점에서 2302번과 유사하다.

 

이러한 경우 기본적인 점화식 구성은 다음과 같다.

dp[i] = dp[i - 1] + dp[i - 2];

dp[i]가 의미하는 바는 i번째까지 가능한 경우의 수이다.

1. 바로 전에 있는 i-1번째 문자와 묶어서 해석하는 경우의 수 = dp[i-2] (i번째와 i-1번째를 제외하고 생각한다고 가정하면 직관적이다)

2. i번째 수를 있는 그대로 해석하는 경우의 수 =  dp[i-1]

 

하지만 이 문제에서 암호화될 수 없는 케이스가 존재한다. 

1.  한자리수로 해석할 때 숫자가 0이라면 불가능하다.

2. 두자리수로 해석할 때 숫자가 10~26사이가 아닌 경우는 불가능하다.

 

이 두 케이스를 조건화해서 점화식을 전개하면 답을 구할 수 있다.

 

코드

#include <iostream>
#include <vector>
#include <algorithm>
#include <string>
#define endl "\n"

using namespace std;

int dp[5001];
string s;

void Solve() {
	bool check1, check2;
	int num;
	cin >> s;
	if (s[0] != '0') dp[0] = 1;
	else {
		cout << 0; return;
	}
	if (s.size()>1&&s[1] != '0') dp[1] = 1;
	if ((s[0] - '0') * 10 + s[1] - '0' >= 10 && (s[0] - '0') * 10 + s[1] - '0' <= 26) dp[1]+=1;
	for (int i = 2; i < s.size(); i++) {
		check1 = check2 = false;
		
		if (s[i] != '0') check1 = true;

		num = (s[i - 1] - '0') * 10 + s[i] - '0';
		if (num >= 10 && num <= 26) check2 = true;

		if (check1 && check2) dp[i] = dp[i - 1] + dp[i - 2];
		else if (check1) dp[i] = dp[i - 1];
		else if (check2) dp[i] = dp[i - 2];
		else break;
		
		dp[i] %= 1000000;
	}

	cout << dp[s.size() - 1]% 1000000;
}


int main() {
	ios::sync_with_stdio(false);
	cin.tie(NULL);
	cout.tie(NULL);
	freopen("input.txt", "r", stdin);
	Solve();


	return 0;
}

'PS' 카테고리의 다른 글

[BAEKJOON] 5430 AC (C++)  (0) 2023.07.14
[BAEKJOON] 1987 알파벳 (C++)  (0) 2023.07.13
[프로그래머스] 조이스틱 (C++)  (1) 2023.07.11
[BAEKJOON] 1918 후위 표기식 (C++)  (0) 2023.07.10
[BAEKJOON] 20444 색종이와 가위 (C++)  (0) 2023.07.08