프로그래머스 [H-Index]

JH.P·2022년 7월 20일

문제의 조건을 그대로 구현한 풀이

function solution(citations) {
    let max = Math.max(...citations)     // 최대값(h)
    // h번 이상 인용된 논문이 h번 이상이고,
    // 나머지 논문이 h번 이하 인용되었다.
    // 이때 h의 최대값을 구하여라
    
    // 1. 인용 배열에서 최대값을 구하자.
    // 2. 값이 (최대값) 이상인 요소들이 (최대값)개 이상인지?
    // 3. 2번 조건을 만족한다면 나머지 요소들이 값이 모두 최대값 이하인지? 
    // 4. 조건을 만족할 때까지 최대값을 1씩 감소시키자.
    
    while(1) {
       let maxArr = []
       // arr의 요소들이 최대값 이상인 요소들이 최대값 개 이상인지 검사
       for(let i = 0; i < citations.length; i++) {
           if(citations[i] >= max) {
               maxArr.push(citations[i])
           }
       }
        if(maxArr.length >= max) {      // h번 이상 인용된 논문이 h편 이상인 경우
            // 나머지 요소들은 h 이하인지 검사 => 맞으면 max 반환
            return max
        } else {                    // 그렇지 않은 경우
            max -= 1
            continue;
        }
    }
}

위 과정을 요약하면 다음과 같다.

  • 문제의 요구사항인 인용 횟수가 h 이상인 요소의 갯수가 h 이상인 값을 구한다.
  • 이 중 가장 큰 최대값을 구해야 한다.
  • 제시된 인용 횟수 배열 중 최대값을 구하고, while loop 안에서 해당 조건에 일치하는지를 검사한다. 최대값에서 부터 시작해야, 조건에 일치하는 가장 큰 값을 찾을 수 있기 떄문이다.
  • 조건에 일치하면 즉시 해당 값을 반환한다.
  • 만약 일치하지 않으면 최대값에서 1을 차감하고, 다시 반복문 내 동작을 수행한다.

정렬

  • 위의 코드대로 작성하여 테스트 케이스를 전부 통과하긴 했지만, 유형이 정렬로 분류되어있는 것을 보니, 정렬을 이용한 풀이를 요구하는 것 같다.
  • 다른 사람의 풀이를 참고하여보니, 아래와 같이 단 4줄로 끝나는 코드를 발견하였다.
function solution(citations) {
    let hIndex = 0;
    citations.sort((a,b)=>(b-a))
    
    while(hIndex + 1 <= citations[hIndex]){
        hIndex++;
    }
    return hIndex
}
  • 위 코드의 내용은 다음과 같은 과정을 거친다.
  • 우선 인용 횟수가 담긴 배열을 내림차순 "정렬"시키고
  • 그리고 내림차순 정렬된 인용 횟수 배열을 while loop 내에서 순회한다.
  • h-Index + 1(현재 측정된 배열 요소의 갯수)가 현재 순회중인 요소의 인용된 횟수보다 커지면, 반복문을 종료한다.
  • 즉 h-지수는 인용횟수가 h 이상인 요소의 갯수가 h 이상인 값 중 최대값이기 때문에, 내림차순 정렬을 먼저 하고 위 과정을 거친 것이다.
  • hIndex를 반환한다.
  • 어느 정도 감이 잡히긴 했어도 완벽히 이해가 된 것은 아니라, 반복해서 위 코드를 보고 내용을 이해해야겠다..!
profile
꾸준한 기록

0개의 댓글