ABOUT ME

Today
Yesterday
Total
  • [프로그래머스]-호텔 대실
    알고리즘/Level 2 2023. 2. 3. 13:59

    https://school.programmers.co.kr/learn/courses/30/lessons/155651

     

    프로그래머스

    코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.

    programmers.co.kr

    접근 방법

    해당 문제는 정렬을 사용한 후 시간을 비교해 푸는 방법으로 접근하였다. 

    그러므로 sort()함수를 정확하게 알고 있어야 문제를 보다 쉽게 풀 수 있다. 

    고려해야할 사항은 아래와 같다.

    • 시작 시간에 맞게 시간을 정렬해준다. 
    • "이전 대실 종료 시각 + 10분 <= 시작 시간" 이라는 조건을 만족해야 한다.
    • 최대 가능한 시간은 23시 59분이다. 

    풀이

    문자열을 숫자로 이루어진 배열로 변경

    function solution(book_time){
      const arr = book_time.map((el) => {
        let num1 = el[0].split(':');
        // 11:23 => [11,23]
        let num2 = el[1].split(':'); 
        // string 타입을 parseInt를 통해 number타입으로 변경
        let hour1 = parseInt(num1[0] * 60) + parseInt(num1[1]);
        // [시간 + 분 + 청소시간 10분]
        let hour2 = parseInt(num2[0] * 60) + parseInt(num2[1]) + 10; 
        return [hour1, hour2];
      });
    }

    먼저 주어진 시간을 숫자 타입으로 변경해야 하는데 시간과 분을 나누기 위해 : 를 기준으로 split을 해주었다. 

    그후 시간을 그대로 반환하는 것이 아닌 시간에 60을 곱하여 분으로 변경해주었다.이렇게 해준 이유는 후반에 가면 알 수 있다. 

    그리고 시간과 분을 더하고, 종료시간의 경우 청소시간 10분까지 더한 뒤에 이를 배열의 형태로 반환하였다. 

    시작시간을 기준으로 오름차순 정렬

     arr.sort((a, b) => {
        return a[0] - b[0];
      });

     

    시작 시간을 오름차순으로 정렬하여 비교하기 위해 sort함수를 사용

    시작 시간과 종료시간을 비교하며 방 크기 카운트

    let local = 0;
    arr.forEach((el, idx) => {
        local = el[1];
        for (let i = idx + 1; i < arr.length; i++) {
          if (local <= arr[i][0]) { 
            local = arr[i][1];
            arr[i] = -1;
          }
        }
        if (el !== -1) count++;
      });
    
      return count;

     

     

     

     

     

    이제부터 배열을 반복하며 시작시간이 이전 종료시간보다 늦은 경우를 찾으면 된다 .

    먼저 전역으로 선언한 local변수에 현재의 종료 시간을 넣은 후 for문을 통해 다음 배열의 시작시간을 비교해주면 된다 .

    만약 시작시간이 이전 종료시간보다 늦은 경우에는 해당 인덱스의 종료시간을 전역변수에 할당한 뒤 그 인덱스의 값을 -1로 덮어 씌워준다. 

    이렇게 -1로 덮어 씌운 이유는 해당 시간이 중복으로 들어가는 경우를 제거하기 위해 한번 사용이 되었다면 그 값을 사용하지 못하게 하기 위해서 값을 변경해줘야 한다. 

    그후 모든 값을 탐색하였다면 현재 값이 -1이 아닐 경우에 카운트를 해주면 된다. 여기서 왜 -1이 나오지라는 생각이 들 수 있다. 

    예를 들어 설명을 해보겠다.

    [["15:00", "17:00"], ["16:40", "18:20"], ["14:20", "15:20"], ["14:10", "19:20"], ["18:20", "21:20"]]
    이를 오름차순으로 정렬한다면 아래와 같다.
    [["14:10", "19:20"],["14:20", "15:20"],["15:00", "17:00"], ["16:40", "18:20"],["18:20", "21:20"]]

    그럼 종료시간을 기준으로 비교해가면 된다.
    첫번째 종료시간인 19:30분보다 늦은 시작시간은 하나도 없으니 el의 값은 -1이 아니므로 카운트를 증가해주자.count = 1

    두번째 종료시간인 15:30분보다 늦은 시간을 찾으면 16:40분이 있다.
    그럼 해당 종료시간이 local(=18:30) 에 들어갈 것이고, 해당 배열을 -1로 바꿔줘 보고 18시 30분보다 늦은 시작시간은 없으니 이대로 종료가 된다. 현재 el값은 ["14:20", "15:20"]이기 때문에 -1이 아니므로 카운트를 증가해주자.count = 2
    [["14:10", "19:20"],["14:20", "15:20"],["15:00", "17:00"], -1,["18:20", "21:20"]]

    세번째 종료시간인 17:10분보다 늦은 시작 시간을 찾으면 18:20분이 있다. 
    그럼 해당 종료시간이 local(=21:30) 에 들어갈 것이고, 해당 배열을 -1로 바꿔줘 보고 21시 30분보다 늦은 시작시간은 없으니 이대로 종료가 된다. 현재 el값은 ["15:00", "17:00"]이기 때문에 -1이 아니므로 카운트(3)를 증가해주자.  count = 3
    [["14:10", "19:20"],["14:20", "15:20"],["15:00", "17:00"], -1,-1]

    네번째 종료시간을 알기위해 배열 돌려고하지만 현재 el의 값은 -1이기 때문에 시작시간을 비교하지 못해고 카운트도 증가시키지 못한다.  이와 같이 5번째 종료시간도 동일하게 카운트를 증가시키지 못하게 된다. 

    그럼 총 필요한 방의 갯수는 count의 수인 3개

    시간을 분으로 바꿔서 연산한 이유는 다음과 같다. 

    처음에는 11:23분이면 1123이처럼 단순하게 숫자를 연결하여 비교를 하였다. 

    하지만 2문제에서 자꾸 오류가 발생하였다. 최대한 테스트 케이스를 추가해 풀어보았지만 왜 오류가 발생하였는지를 찾지는 못하였다.

    그래서 조금 귀찮더라도 시간을 분으로 바꿔서 연산을 해보았는데 해당 오류가 없어졌다....

    만약 이 글을 읽고 나는 시간을 분으로 안바꾸고 풀어봐야지 라고 생각한 사람들이 있다면 꼭 풀어서 댓글로 알려주길 바란다... 

     

Designed by Tistory.