Skip to main content

[Java] 12926 시저암호


1. 문제

시저암호


2. 정답코드

내가 푼 방법은 엄밀히 말하면 좋은 코드는 아니다.
Z에서 한 칸 밀면 다시 A가 되고, z에서 밀면 a되는 걸 구현하는 부분에서 생각이 오래 걸렸다.

나는 단순하게 생각해서 A부터 Z까지 알파벳을 repeat()메서드로 두 번 이어 붙여서 해결했다.

ABCDEFGHIJKLMNOPQRSTUVWXYZABCDEFGHIJKLMNOPQRSTUVWXYZ

for문으로 s를 순회하면서

  1. 대문자면 upper에서 n만큼 인덱스 이동
  2. 소문자면 lower에서 n만큼 인덱스 이동
    → 이동한 문자열을 StringBuilder에 추가
  3. 이 때 공백이나 특수문자는 그대로 추가한다.
class Solution {
    public String solution(String s, int n) {
        String upper = "ABCDEFGHIJKLMNOPQRSTUVWXYZ".repeat(2);
        String lower = "abcdefghijklmnopqrstuvwxyz".repeat(2);
        StringBuilder sb = new StringBuilder();

        for (int i = 0; i < s.length(); i++) {
            char c = s.charAt(i);

            if (c >= 'a' && c <= 'z') {
                int idx = c - 'a';          // 소문자 기준 인덱스
                sb.append(lower.charAt(idx + n)); // n만큼 이동
            } else if (c >= 'A' && c <= 'Z') {
                int idx = c - 'A';          // 대문자 기준 인덱스
                sb.append(upper.charAt(idx + n)); // n만큼 이동
            } else {
                sb.append(c); // 공백이나 특수문자는 그대로
            }
        }

        return sb.toString();
    }
}

그리고 소문자 'a'는 아스키 97, 대문자 'A'는 아스키 65라서 if문 분기점에서 웬만하면 소문자 먼저 쓰는게 좋다

repeat() 쓰지않고 아스키로만 구현한 코드

class Solution {
    public String solution(String s, int n) {
        StringBuilder sb = new StringBuilder();

        for (int i = 0; i < s.length(); i++) {
            char c = s.charAt(i);

            if (c >= 'a' && c <= 'z') {           // 소문자 먼저 처리
                sb.append((char) ('a' + (c - 'a' + n) % 26));
            } else if (c >= 'A' && c <= 'Z') {    // 그 다음 대문자 처리
                sb.append((char) ('A' + (c - 'A' + n) % 26));
            } else {
                sb.append(c);                     // 공백, 숫자, 특수문자는 그대로
            }
        }

        return sb.toString();
    }
}
  • 'A' + (c - 'A' + n) % 26
    'A'를 기준으로 0~25 범위 만든 뒤 n만큼 이동하고,
    26으로 나눈 나머지로 Z 넘어가는 걸 처리
  • 'a' + (c - 'a' + n) % 26
    소문자로 동일하게 처리
  • 공백, 숫자는 그대로 붙임
(char) ('a' + (c - 'a' + n) % 26)

1. (c - 'a')

  • 'c'가 예를 들어 'b'라고 하면
    • 'b' - 'a' = 98 - 97 → 1
  • 즉, 문자를 0~25 범위 인덱스로 바꾼 것
    • 'a'는 0, 'b'는 1, .... 'z'는 25

2. (c - 'a' + n) % 26

  • n만큼 밀고, 26으로 나머지 연산해서 Z넘어가면 다시 A로 돌아가게 처리하는 것이다
  • 예를 들면 'z'+ 2 하면 (25 +2) % 26 = 1 이다. 1은 'b'가 된다.

3. 'a' + (...)

  • 지금 위에까지 계산 결과는 0~25 숫자인데
  • 다시 실제 아스키코드 문자로 변환하려면 'a'를 더해야 함
  • 여기서 'a' 더하는 이유는 0~25 범위로 계산한 값을 다시 아스키 문자로 되돌리기 위해서이다.