본문 바로가기
Algorithms & CS

[JAVA] 프로그래머스 - 모의고사

by 고막고막 2019. 7. 11.

문제 설명

수포자는 수학을 포기한 사람의 준말입니다. 수포자 삼인방은 모의고사에 수학 문제를 전부 찍으려 합니다. 수포자는 1번 문제부터 마지막 문제까지 다음과 같이 찍습니다.

1번 수포자가 찍는 방식: 1, 2, 3, 4, 5, 1, 2, 3, 4, 5, ...
2번 수포자가 찍는 방식: 2, 1, 2, 3, 2, 4, 2, 5, 2, 1, 2, 3, 2, 4, 2, 5, ...
3번 수포자가 찍는 방식: 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, 3, 3, 1, 1, 2, 2, 4, 4, 5, 5, ...

1번 문제부터 마지막 문제까지의 정답이 순서대로 들은 배열 answers가 주어졌을 때, 가장 많은 문제를 맞힌 사람이 누구인지 배열에 담아 return 하도록 solution 함수를 작성해주세요.

제한 조건

  • 시험은 최대 10,000 문제로 구성되어있습니다.
  • 문제의 정답은 1, 2, 3, 4, 5중 하나입니다.
  • 가장 높은 점수를 받은 사람이 여럿일 경우, return하는 값을 오름차순 정렬해주세요.

Solution

import java.util.*;

public class Test4 {
	public static int[] solution(int[] answers) {
    
		// 1. 각각의 수포자가 찍을 정답 배열을 생성해 값을 담는다
		int[] supoja1Answer = new int[10000];
		int[] supoja2Answer = new int[10000];
		int[] supoja3Answer = new int[10000];
		int[] supoja1Rule = { 1, 2, 3, 4, 5 };
		int[] supoja2Rule = { 2, 1, 2, 3, 2, 4, 2, 5 };
		int[] supoja3Rule = { 3, 3, 1, 1, 2, 2, 4, 4, 5, 5 };

		int i1 = 0, i2 = 0, i3 = 0;
		while (i1 < 10000) {
			for (int j = 0; j < supoja1Rule.length; j++) {
				supoja1Answer[i1] = supoja1Rule[j];
				i1++;
			}
		}
		while (i2 < 10000) {
			for (int j = 0; j < supoja2Rule.length; j++) {
				supoja2Answer[i2] = supoja2Rule[j];
				i2++;
			}
		}
		while (i3 < 10000) {
			for (int j = 0; j < supoja3Rule.length; j++) {
				supoja3Answer[i3] = supoja3Rule[j];
				i3++;
			}
		}

		// 2. 정답과 대조해 각각의 수포자가 맞춘 갯수를 합산
		int supoja1Score = 0;
		int supoja2Score = 0;
		int supoja3Score = 0;

		for (int i = 0; i < answers.length; i++) {
			if (supoja1Answer[i] == answers[i])
				supoja1Score++;
			if (supoja2Answer[i] == answers[i])
				supoja2Score++;
			if (supoja3Answer[i] == answers[i])
				supoja3Score++;
		}

		// 3. 순위 산출해서 answer 배열에 담아 리턴        
        int cnt = 0;	// answer 배열의 길이를 저장
		int[] winner = new int[3];
		if (supoja1Score > supoja2Score && supoja1Score > supoja3Score) {
			winner[0] = 1;
			cnt = 1;
		} else if (supoja2Score > supoja1Score && supoja2Score > supoja3Score) {
			winner[0] = 2;
			cnt = 1;
		} else if (supoja3Score > supoja1Score && supoja3Score > supoja2Score) {
			winner[0] = 3;
			cnt = 1;
		} else if (supoja1Score == supoja2Score && supoja1Score > supoja3Score) {
			winner[0] = 1;
			winner[1] = 2;
			cnt = 2;
		} else if (supoja2Score == supoja3Score && supoja2Score > supoja1Score) {
			winner[0] = 2;
			winner[1] = 3;
			cnt = 2;
		} else if (supoja1Score == supoja3Score && supoja1Score > supoja2Score) {
			winner[0] = 1;
			winner[1] = 3;
			cnt = 2;
		} else if (supoja1Score == supoja3Score && supoja1Score > supoja2Score) {
			winner[0] = 1;
			winner[1] = 3;
			cnt = 2;
		} else if (supoja1Score == supoja3Score && supoja1Score == supoja2Score) {
			winner[0] = 1;
			winner[1] = 2;
			winner[2] = 3;
			cnt = 3;
		}
        
		int[] answer = new int[cnt];
		for (int i = 0; i < answer.length; i++) {
			answer[i] = winner[i];
		}
		return answer;
	}
}

구글링 하지 않고 수제코딩 해보자는 결심을 지키기 위해 배열 관련 내장함수가 기억이 안 났으나 안 찾아보고 모든 경우의 수를 다 if문에 넣고 돌린 결과...자괴감................................근데 내장함수를 안 쓴 문제만은 아니고 총체적 난국.

다른 사람 풀이 중 ㅈㄴ 아름답게 짰다고 생각한 코드 가져옴.

import java.util.*;

class Solution {
    public int[] solution(int[] answers) {
        int[] arr = new int[3];
        int[] a = {5,1,2,3,4};
        int[] b = {5,2,1,2,3,2,4,2};
        int[] c = {5,3,3,1,1,2,2,4,4,5};

        for(int i = 0; i < answers.length; i++){
            if(answers[i] == a[(i+1)%5]) arr[0]++;
            if(answers[i] == b[(i+1)%8]) arr[1]++;
            if(answers[i] == c[(i+1)%10]) arr[2]++;
        }

        int max = arr[0];

        if(max < arr[1]) max = arr[1];
        if(max < arr[2]) max = arr[2];

        if(max == arr[0] && max == arr[1] && max == arr[2]) return new int[]{1,2,3};
        else if(max == arr[0] && max == arr[1]) return new int[]{1,2};
        else if(max == arr[0] && max == arr[2]) return new int[]{1,3};
        else if(max == arr[1] && max == arr[2]) return new int[]{2,3};
        else if(max == arr[0]) return new int[]{1};
        else if(max == arr[1]) return new int[]{2};

        return new int[]{3};
    }
}

- 채점시 입력은 알아서 만 미만일 것이기 때문에 들어오는 배열을 그대로 받아 그 길이 안에서만 일치하는 갯수를 세면 되는거였다.
- 어차피 수포자가 찍을 답들은 반복되기 때문에 맨 뒤에 값을 맨 앞으로 가져와서 채점할때는 인덱스 0이 아닌 1부터 시작. (1회전일 때도 몫이 0이고 나머지가 1부터 나오기 때문에 무관함) 

올라가즈아