코딩 테스트/프로그래머스

프로그래머스 - N진수 게임 문제 (자바)

programmers.co.kr/learn/courses/30/lessons/17687#

 

코딩테스트 연습 - [3차] n진수 게임

N진수 게임 튜브가 활동하는 코딩 동아리에서는 전통적으로 해오는 게임이 있다. 이 게임은 여러 사람이 둥글게 앉아서 숫자를 하나씩 차례대로 말하는 게임인데, 규칙은 다음과 같다. 숫자를 0

programmers.co.kr

 

0부터 특정 진법으로 변환한 값을 m 명이 t번 말하는 경우까지 구하고

해당 문자열에서 튜브의 순서의 값들만 구해서 리턴하면 끝이다.

사실상 숫자를 특정 진법으로 변환하는 방법을 알면 풀수있는 문제라고 볼수있다.

 

8를 2진법으로 하면 1000인데 이를 보면

8 / 2 = 4

8 % 2 = 0

 

4 / 2 = 2

4 % 2 = 0

 

2 / 2 = 1 

2 % 2 =0

 

진법보다 낮아진 몫 1

몫이 진법보다 낮아질때 까지의 나머지 값들 0, 0, 0  

이 둘을 이용해서 8을 2진법으로 나타낸 1000을 구할 수 있다.

 

주의점은 진법이 11 진법이상인 경우 알파벳이 등장하기 때문에 나머지값이나 진법보다 낮아진 몫이 10이상인 경우 알파벳으로 셋팅하도록 해야한다.

class Solution {
    public String solution(int n, int t, int m, int p) {
        StringBuilder sb = new StringBuilder();
        StringBuilder answer = new StringBuilder();

        int num = 0;

        // m명이 t번 말하는 경우까지 구함
        while(sb.length() < m * t) {
            sb.append(calc(num++, n));
        }

        // 문자열은 0부터 이므로 p-1부터
        // 튜브가 말할 것만 알면되기 때문에 +m 씩 증가
        for(int i = p - 1; i < m * t; i = i + m) {
            answer.append(sb.charAt(i));
        }
        return answer.toString();
    }

    // num을 radix 진법으로 변환
    public String calc(int num, int radix) {
        StringBuilder sb = new StringBuilder();

        // 만약 진법 변환할 숫자가 진법보다 큰 경우
        while(num >= radix) {
            sb.append(isMoreThanTen(num % radix));
            num = num / radix;
        }
        // 진법보다 작아진 수를 추가
        sb.append(isMoreThanTen(num));

        // 뒤집어서 리턴 - > 8을 2진법으로 위 로직을 돌리면 0001 됨
        return sb.reverse().toString();
    }

    // 10 이상의 숫자를 알파벳으로 변환(11진법 이상에서 A와 같은 알파벳을 위해)
    public char isMoreThanTen(int n) {
        if (n >= 10) {
            return (char) (n - 10 + 'A');
        }
        return (char) (n + '0');
    }
}

자바에서 제공하는 Integer.toString(숫자, 진법)을 이용하면 진법을 변경을 알아서 해준다.

class Solution {
    public String solution(int n, int t, int m, int p) {
        StringBuilder sb = new StringBuilder();
        StringBuilder answer = new StringBuilder();

        int num = 0;

        // m명이 t번 말하는 경우까지 구함
        while(sb.length() < m * t) {
            sb.append(Integer.toString(num++, n));
        }

        // 문자열은 0부터 이므로 p-1부터
        // 튜브가 말할 것만 알면되기 때문에 +m 씩 증가
        for(int i = p - 1; i < m * t; i = i + m) {
            answer.append(sb.charAt(i));
        }
        return answer.toString().toUpperCase();
    }
}