[프로그래머스/JS] 구명보트

코린·2023년 6월 20일
0

알고리즘

목록 보기
18/44
post-thumbnail

문제

문제 설명

무인도에 갇힌 사람들을 구명보트를 이용하여 구출하려고 합니다. 구명보트는 작아서 한 번에 최대 2명씩 밖에 탈 수 없고, 무게 제한도 있습니다.

예를 들어, 사람들의 몸무게가 [70kg, 50kg, 80kg, 50kg]이고 구명보트의 무게 제한이 100kg이라면 2번째 사람과 4번째 사람은 같이 탈 수 있지만 1번째 사람과 3번째 사람의 무게의 합은 150kg이므로 구명보트의 무게 제한을 초과하여 같이 탈 수 없습니다.

구명보트를 최대한 적게 사용하여 모든 사람을 구출하려고 합니다.

사람들의 몸무게를 담은 배열 people과 구명보트의 무게 제한 limit가 매개변수로 주어질 때, 모든 사람을 구출하기 위해 필요한 구명보트 개수의 최솟값을 return 하도록 solution 함수를 작성해주세요.

제한사항

  • 무인도에 갇힌 사람은 1명 이상 50,000명 이하입니다.
  • 각 사람의 몸무게는 40kg 이상 240kg 이하입니다.
  • 구명보트의 무게 제한은 40kg 이상 240kg 이하입니다.
  • 구명보트의 무게 제한은 항상 사람들의 몸무게 중 최댓값보다 크게 주어지므로 사람들을 구출할 수 없는 경우는 없습니다.

입출력 예

peoplelimitreturn
[70, 50, 80, 50]1003
[70, 80, 50]1003

문제 풀이

요 문제는 말입니다. 바로 탐욕법(Greedy) 알고리즘을 사용하는 문제입니다!

그렇다면 오늘도 탐욕법이 뭔지 알고 가야겠져?

그리디 알고리즘

현재 상황에서 최적의 해를 찾는 것 입니다!

그리디 알고리즘으로 최적해를 도출하기 위해서는 아래 두가지 조건을 만족해야 한다.

1.탐욕적 선택 속성 (greedy choice property)

탐욕적인 선택이 항상 안전하다는 것이 보장된다는 의미이다. 즉, 그리디한 선택이 언제나 최적해를 보장해야한다.

2. 최적 부분 구조 (optimal substructure)

부분 최적해(Local optimum)들이 모여 전체 최적해(Global optimum)를 구할 수 있는 경우이다. 즉, 전체 문제가 여러 부분 문제로 분할되며, 이 단계 하나하나에 대한 최적해가 도출되어야 한다는 의미이다.

우리 문제에서는 어떤 방식으로 최적해를 찾느냐!

내림 차순으로 정렬하고 큰수와 작은수를 순서대로 더하는 것이 최적의 해 입니다.

잘못생각한점

보트엔 2명씩만 탈 수 있다!! ⇒ 문제를 꼼꼼히 볼 필요가 있다!

오름차순으로 정렬해서 작은수끼리 더하는 것이 최적의 해는 아닙니다.

탐색할 때 종료되는 시점은 앞에서 부터 탐색하던 것과 뒤에서 부터 탐색하던 것이 만나는 순간이라는 것!

결과 코드

function solution(people, limit) {
    var answer = 0;
    
    //내림 차순 정렬
    people.sort((a,b)=> b-a);
    
    //뒤에서 부터 탐색할 인덱스
    let j = people.length -1; 
    
    //앞에서 부터 탐색
    for(let i=0;i<= j;i++){
        if(people[i] + people[j] <= limit){ 
            j--; //넘지 않는 경우는 같이 태우면 되므로 answer++을 안하는 것
        }
        answer++; 
    }
    
    return answer;
}

.
.
.
.
.
.
.
.
.
.

기본 알고리즘들을 어디서든 적용할 수 있는 인간이 되기위해 노력하쟈!!!!!!!!!!!!

profile
안녕하세요 코린입니다!

0개의 댓글