[ 프로그래머스 ] 42889 실패율

codesver·2023년 1월 31일
0

Programmers

목록 보기
15/30
post-thumbnail

📌 Analyze

문제 자체는 간단하다.

stages 정보를 바탕으로 각 Stage 별 도착 인원 수와 시도 중인 인원 수를 먼저 계산한다.

계산한 값을 바탕으로 실패율을 구하고 이를 기준으로 정렬한다.

정렬된 순서에 맞게 각 stage 번호를 반환하면 된다.

📌 Solution

Step 0. Stage class

Stage 클래스는 Stage와 관련된 정보를 가진다.

class Stage {

    int num;						// Stage 번호
    int arrive = 0, trial = 0;		// 각각 도착 인원, 시도 중인 인원
    double failure;					// 실패율

    public Stage(int num) {
        this.num = num;
    }
}

Step 1. Stage list 생성

주어진 N에 맞추어 1번부터 N번까지의 Stage를 생성한다.

solution의 stages 인자의 변수명을 S로 바꾸어 해결하였다.

List<Stage> stages = IntStream.rangeClosed(1, N)
        .mapToObj(Stage::new)
        .collect(Collectors.toList());

Step 2. 실패율 계산

주어진 S의 정보를 바탕으로 stages의 실패율을 계산한다.

계산 방법은 stages를 하나식 탐색한다.

탐새할 때는 S의 정보를 바탕으로 arrive와 trial를 우선 계산하다.

이후 failure를 계산한다.

stages.forEach(stage -> stage.update(S));

public void update(int[] S) {
    for (int s : S) {
        if (s >= num) arrive++;
        if (s == num) trial++;
    }
    calcAvg();
}

Step 3. 실패율 정렬

실패율을 모두 계산하였으면 이를 기준으로 정렬한다.

이 때 내림차순으로 정렬해야 한다.

stages.sort(Comparator.comparingDouble(s -> -s.failure));

Step 4. 반환

정렬이 완려되었으면 List를 int[]로 변환하여 반환한다.

return stages.stream().mapToInt(stage -> stage.num).toArray();

Step Z. 정리

위의 모든 과정들은 사실 Stream으로 처리할 수 있다.

따라서 하나의 Stream으로 처리한다.

return IntStream
        .rangeClosed(1, N)
        .mapToObj(Stage::new)									// Stage 생성
        .peek(stage -> stage.update(S))							// 실패율 계산
        .sorted(Comparator.comparingDouble(s -> -s.failure))	// 실패율 정렬
        .mapToInt(Stage::getNum).toArray();						// 변환 및 반환

📌 Code

GitHub Repository

Solution

class Solution {
    public int[] solution(int N, int[] S) {
        return IntStream
                .rangeClosed(1, N)
                .mapToObj(Stage::new)
                .peek(stage -> stage.update(S))
                .sorted(Comparator.comparingDouble(s -> -s.failure))
                .mapToInt(Stage::getNum).toArray();
    }
}

Stage

class Stage {

    int num;
    int arrive = 0, trial = 0;
    double failure;

    public Stage(int num) {
        this.num = num;
    }

    public void update(int[] S) {
        for (int s : S) {
            if (s >= num) arrive++;
            if (s == num) trial++;
        }
        calcAvg();
    }

    public void calcAvg() {
        failure = arrive == 0 ? 0 : trial / (double) arrive;
    }

    public int getNum() {
        return num;
    }
}
profile
Hello, Devs!

0개의 댓글