본문 바로가기
코딩테스트-기록

[프로그래머스] 중복값 개수 구하기

by SeongwooLee 2024. 1. 9.

 

코딩테스트 풀다 방법3개가 있어서 chatGPT도 활용. 해석하며 작성해본다.

 

참고로 저는 reduce()를 활용해서 풀이했습니다...!

 

문제

 

최빈값은 주어진 값 중에서 가장 자주 나오는 값을 의미한다.

정수 배열 array가 매개변수로 주어질 때, 최빈값을 return 하도록 solution 함수를 완성한다.

최빈값이 여러 개면 -1을 return 한다.


 

▼ 입출력 예시

array result
[1, 2, 3, 3, 3, 4] 3
[1, 1, 2, 2] -1
[1] 1

 

 

▼ 입출력 예 설명

 

  입출력 예 #1

  • [1, 2, 3, 3, 3, 4]에서 1은 1개 2는 1개 3은 3개 4는 1개로 최빈값은 3이다.

  입출력 예 #2

  • [1, 1, 2, 2]에서 1은 2개 2는 2개로 최빈값이 1, 2입니다. 최빈값이 여러 개이므로 -1을 return 한다.

  입출력 예 #3

  • [1]에는 1만 있으므로 최빈값은 1이다.

 

 

ES6
1. Map(), for of()

function solution(array) {
    let countMap = new Map();  // 숫자의 등장 횟수를 저장할 Map 객체 생성

    // 배열의 각 요소를 순회하며 등장 횟수를 countMap에 저장
    for (let i = 0; i < array.length; i++) {
        let num = array[i];
        if (countMap.has(num)) {
            countMap.set(num, countMap.get(num) + 1);  // 이미 등장한 숫자라면 count 1 증가
        } else {
            countMap.set(num, 1);  // 처음 등장한 숫자라면 count를 1로 설정
        }
    }

    let maxCount = 0;  // 최빈값의 등장 횟수를 저장할 변수 초기화
    let mode = [];  // 최빈값을 저장할 배열 초기화

    // countMap을 순회하며 최빈값과 그 등장 횟수를 찾음
    for (let [key, value] of countMap) {
        if (value > maxCount) {
            maxCount = value;  // 최빈값의 등장 횟수 갱신
            mode = [key];  // 최빈값을 mode 배열에 저장
        } else if (value === maxCount) {
            mode.push(key);  // 최빈값이 여러 개라면 mode 배열에 추가
        }
    }

    if (mode.length > 1) {
        return -1;  // 최빈값이 여러 개면 -1 반환
    } else {
        return mode[0];  // 최빈값 반환
    }
}

 

▲ 1. Map 객체를 사용하여 숫자의 등장 횟수를 저장하는데 탁월

     2. Map 객체는 key-value 쌍을 저장하며, key를 중복해서 저장 불가능

     3. has, get, set 등의 메서드를 활용하여 간편하게 처리 가능

최빈값 찾는 과정에서 등장 횟수를 비교. 최빈값을 업데이트하고, 최빈값이 여러 개인 경우 배열에 저장하는 방식으로 처리

-
2. for(), for in()

function solution(array) {
    let count = {};  // 숫자의 등장 횟수를 저장할 객체 생성

    for (let i = 0; i < array.length; i++) {
        let num = array[i];
        count[num] = (count[num] || 0) + 1;
    }

    let mode = -1;
    let maxCount = 0;

    for (let key in count) {
        if (count.hasOwnProperty(key)) {
            if (count[key] > maxCount) {
                maxCount = count[key];
                mode = parseInt(key);
            } else if (count[key] === maxCount) {
                mode = -1;
            }
        }
    }

    return mode;
}

 

▲ 1. 객체 count를 사용하여 각 숫자의 등장 횟수를 효율적으로 저장하고 관리

     2. 배열을 1번 순회하면서 등장 횟수 계산, 2번째 순회에서 최빈값 찾기. 이로 인한 시간 복잡도 O(n)으로 비교적 효율적

ES6
3. reduce()

function solution(array) {
    let count = array.reduce(function(acc, curr) {
        acc[curr] = (acc[curr] || 0) + 1;
        return acc;
    }, {});

    let mode = -1;
    let maxCount = 0;

    for (let key in count) {
        if (count.hasOwnProperty(key)) {
            if (count[key] > maxCount) {
                maxCount = count[key];
                mode = parseInt(key);
            } else if (count[key] === maxCount) {
                mode = -1;
            }
        }
    }

    return mode;
}

 

▲ 1. reduce 함수를 사용하여 숫자의 등장 횟수를 효율적으로 저장하고 관리

     2. 반복문을 사용하여 최빈값을 찾는 과정이 구현

 

 

 

다른 사람의 풀이 中

function solution(array) {
    let m = new Map();
    for (let n of array) m.set(n, (m.get(n) || 0)+1);
    m = [...m].sort((a,b)=>b[1]-a[1]);
    return m.length === 1 || m[0][1] > m[1][1] ? m[0][0] : -1;
}

 

화살표함수, 삼항연산자 이용한 간략한 코드 처리
배열로 변환. 정렬하여 최빈값 찾는 과정을 간략하게 표현한 점 등 감탄하며 배움