이번에는 백준 11655번 ROT13 문제를 풀어보았습니다.
이 문제는 문자열의 각 알파벳을 13글자씩 밀어서 변환하는 문제입니다.
ROT13은 카이사르 암호의 일종으로, 알파벳을 13글자씩 밀어서 만드는 방식입니다.
예를 들어
A → NB → Oa → nb → o처럼 변환됩니다.
알파벳 대문자와 소문자에만 적용되고,
공백이나 숫자 같은 문자는 그대로 출력해야 합니다.
문자열을 처음부터 끝까지 순회하면서 각 문자가
를 먼저 구분했습니다.
알파벳이라면 아스키 코드 기준으로 13을 더하고,
범위를 넘어가면 다시 처음 문자로 돌아오도록 처리했습니다.
예를 들어 대문자에서 Z를 넘어가면 A부터 다시 시작하고,
소문자에서 z를 넘어가면 a부터 다시 시작하도록 만들었습니다.
#include <bits/stdc++.h>
using namespace std;
int check_alphabet(char c) {
if (c >= 'A' && c <= 'Z') {
return 1;
} else if (c >= 'a' && c <= 'z') {
return 2;
}
return 0;
}
int main() {
string input;
string output = "";
getline(cin, input);
for (char c : input) {
int tmp;
int check = check_alphabet(c);
if (check) {
tmp = c + 13;
if (check == 1 && tmp > 'Z') {
tmp = tmp - 'Z' + 'A' - 1;
} else if (check == 2 && tmp > 'z') {
tmp = tmp - 'z' + 'a' - 1;
}
} else {
tmp = c;
}
output += (char)tmp;
}
cout << output;
return 0;
}
getline()으로 문자열 전체를 입력받는다.getline() 사용이 문제는 문자열 중간에 공백이 들어올 수 있기 때문에 cin >> input 대신 getline(cin, input)을 사용했습니다.
getline(cin, input);
이렇게 해야 한 줄 전체를 입력받을 수 있습니다.
ROT13은 대문자와 소문자에 각각 적용되기 때문에,
현재 문자가 어떤 범위에 있는지 먼저 확인해야 했습니다.
int check_alphabet(char c) {
if (c >= 'A' && c <= 'Z') {
return 1;
} else if (c >= 'a' && c <= 'z') {
return 2;
}
return 0;
}
char 대신 int를 사용한 이유노션에 정리해둔 내용처럼, char는 signed char일 경우 범위가 -128 ~ 127일 수 있습니다.
그래서 중간 계산에서는 tmp를 int로 사용하고,
마지막에 결과 문자열에 넣을 때만 char로 캐스팅했습니다.
int tmp;
...
output += (char)tmp;