[프로그래머스 / JAVA] Level 1 모의고사 (42840)
⏰ 2021-12-14 (화) 22:02:01
모의고사
랭크 | 사용 언어 |
---|---|
Level 1 |
🔗 🔗 모의고사
문제 설명
수포자는 수학을 포기한 사람의 준말입니다. 수포자 삼인방은 모의고사에 수학 문제를 전부 찍으려 합니다. 수포자는 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하는 값을 오름차순 정렬해주세요.
입출력 예
answers | return |
---|---|
{ 1, 2, 3, 4, 5 } | { 1 } |
{ 1, 3, 2, 4, 2 } | { 1, 2, 3 } |
입출력 예 설명
입출력 예 #1
- 수포자 1은 모든 문제를 맞혔습니다.
- 수포자 2는 모든 문제를 틀렸습니다.
- 수포자 3은 모든 문제를 틀렸습니다.
따라서 가장 문제를 많이 맞힌 사람은 수포자 1입니다.
입출력 예 #2
- 모든 사람이 2문제씩을 맞췄습니다.
풀이
- 1번 수포자 패턴 -
[ 1, 2, 3, 4, 5 ]
- 2번 수포자 패턴 -
[ 2, 1, 2, 3, 2, 4, 2, 5 ]
- 3번 수포자 패턴 -
[ 3, 3, 1, 1, 2, 2, 4, 4, 5, 5 ]
수포자마다 패턴도 다르고, 길이도 달라서 생각없이 접근할 순 없다. 각 패턴의 길이가 다르므로 인덱스 방식은 적절하지 않다. 패턴을 컨테이너 벨트처럼 순환시켜, 가장 앞 쪽의 숫자를 비교하는 것이 더 효과적일 것이다.
이를 위해선 각 수포자별로 패턴을 순환시키는 로직이 필요하다. [ 1, 2, 3, 4, 5 ]
-> [ 2, 3, 4, 5, 1 ]
자료구조 중 큐의 특성과 매우 유사하므로, 이 문제는 큐를 적극적으로 활용해볼 생각이다.
각 패턴을 정의할 큐 ONE
, TWO
, THREE
가 있으며, 아래와 같이 초기화를 수행한다.
JAVA
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
private void initQueue() { ONE.clear(); TWO.clear(); THREE.clear(); ONE.add(1); ONE.add(2); ONE.add(3); ONE.add(4); ONE.add(5); TWO.add(2); TWO.add(1); TWO.add(2); TWO.add(3); TWO.add(2); TWO.add(4); TWO.add(2); TWO.add(5); THREE.add(3); THREE.add(3); THREE.add(1); THREE.add(1); THREE.add(2); THREE.add(2); THREE.add(4); THREE.add(4); THREE.add(5); THREE.add(5); }
패턴 순서대로 큐에 데이터를 집어넣는다. poll()
메서드를 통해 가장 앞에 위치한 데이터를 꺼낼 수 있다. poll()
의 경우 데이터 호출과 동시에 데이터가 삭제된다.
정답 비교 후, 사용한 데이터는 다시 큐에 집어넣는다. 이런 구조는 문제의 길이에 관계없이 각 수포자 별로 지속적인 순환이 가능할 것이다.
JAVA
1 2 3 4 5 6 7 8 9 10 11 12 13 14
for (int item : answers) { int one = Objects.requireNonNull(ONE.poll()); int two = Objects.requireNonNull(TWO.poll()); int three = Objects.requireNonNull(THREE.poll()); counts[0] += item == one ? 1 : 0; counts[1] += item == two ? 1 : 0; counts[2] += item == three ? 1 : 0; ONE.add(one); TWO.add(two); THREE.add(three); }
정답 비교는 위와 같다. Objects.requireNonNull
는 poll()
이 NullPointerException
을 유발할 가능성이 있으므로, 관련 경고를 제거하기 위한 조치다.
각 수포자별 큐에서 패턴을 뽑고, 이를 문제의 정답과 비교하여 맞춘 경우 counts
배열에 카운팅한다.
사용한 패턴은 add
메서드를 통해 큐에 다시 집어넣는 것을 확인할 수 있다.
점수를 모두 구했다면, 가장 고득점을 구하고, 고득점을 맞은 수포자를 반환하면 된다.
counts
에서 가장 큰 값을 구하면 아래와 같다.
JAVA
1
int max = Arrays.stream(counts).max().getAsInt();
이후 max
에 해당하는 점수를 받은 모든 인원을 탐색하여 배열로 나타내면 된다.
코드
JAVA
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98
import java.util.ArrayList; import java.util.Arrays; import java.util.LinkedList; import java.util.Objects; import java.util.Queue; /** * 모의고사 클래스 * * @author RWB * @since 2021.12.10 Fri 21:43:26 */ class Solution { private static final Queue<Integer> ONE = new LinkedList<>(); private static final Queue<Integer> TWO = new LinkedList<>(); private static final Queue<Integer> THREE = new LinkedList<>(); /** * 해답 반환 메서드 * * @param answers: [int[]] 최고 득점자 * * @return [int[]] 해답 */ public int[] solution(int[] answers) { initQueue(); int[] counts = { 0, 0, 0 }; for (int item : answers) { int one = Objects.requireNonNull(ONE.poll()); int two = Objects.requireNonNull(TWO.poll()); int three = Objects.requireNonNull(THREE.poll()); counts[0] += item == one ? 1 : 0; counts[1] += item == two ? 1 : 0; counts[2] += item == three ? 1 : 0; ONE.add(one); TWO.add(two); THREE.add(three); } int max = Arrays.stream(counts).max().getAsInt(); ArrayList<Integer> list = new ArrayList<>(); for (int i = 0; i < counts.length; i++) { // 최고 점수를 얻었을 경우 if (counts[i] == max) { list.add(i + 1); } } return list.stream().mapToInt(Integer::intValue).toArray(); } /** * 큐 초기화 메서드 */ private void initQueue() { ONE.clear(); TWO.clear(); THREE.clear(); ONE.add(1); ONE.add(2); ONE.add(3); ONE.add(4); ONE.add(5); TWO.add(2); TWO.add(1); TWO.add(2); TWO.add(3); TWO.add(2); TWO.add(4); TWO.add(2); TWO.add(5); THREE.add(3); THREE.add(3); THREE.add(1); THREE.add(1); THREE.add(2); THREE.add(2); THREE.add(4); THREE.add(4); THREE.add(5); THREE.add(5); } }
🏷️ 태그
읽어주셔서 고마워요!
도움이 되셨다면, 공감이나 댓글을 달아주시는 건 어떤가요?
블로그 운영에 큰 힘이 됩니다.