개발 공부/알고리즘 문제 풀이

[프로그래머스] [3차] 방금그곡 (JavaScript)

종범2 2020. 6. 6. 22:06

문제

프로그래머스 2018 KAKAO BLIND RECRUITMENT [3차] 방금 그 곡

https://programmers.co.kr/learn/courses/30/lessons/17683

 

코딩테스트 연습 - [3차] 방금그곡

방금그곡 라디오를 자주 듣는 네오는 라디오에서 방금 나왔던 음악이 무슨 음악인지 궁금해질 때가 많다. 그럴 때 네오는 다음 포털의 '방금그곡' 서비스를 이용하곤 한다. 방금그곡에서는 TV, ��

programmers.co.kr

언어

바스크립트(JavaScript)

 

접근 방법

  1. m과 musicinfos의 악보 정보 문자열의 모든 문자를 #이 존재하지 않는 문자로 변환한다. 이는 나중에 포함 여부를 확인할 때 더 간단하게 확인하기 위함이다.
  2. 각 음악에서 총 재생한 시간을 구하고 그 시간에 따라 전체 재생한 음을 구한다.
  3. 전체 재생한 음 문자열이 m 문자열을 포함하고 있으면 후보로 지정한다.
  4. 후보 중에 재생 시간이 가장 긴 후보를 뽑는다. 만약 같은 재생 시간이면 먼저 나온 음악을 선택한다.

코드

const KEY = {
    'C':'A',
    'C#':'B',
    'D':'C',
    'D#':'D',
    'E':'E',
    'F':'F',
    'F#':'G',
    'G':'H',
    'G#':'I',
    'A':'G',
    'A#':'k',
    'B':'L'
}
function solution(m, musicinfos) {
    let answerList = [];
    let answer = '';
    let arr = [];
    let newM = [];
    // m을 새로운 문자열로 변환
    for (let i=0; i<m.length; i++){
        if(i<m.length-1 && m[i+1] === '#'){
            newM += KEY[m[i]+'#'];
            i++;
        }else{
           newM += KEY[m[i]];
        }
    }
    // musicinfos를 title, content 속성을 가진 객체의 배열로 변환한다.
    for (let i=0; i<musicinfos.length;i++){
        musicinfos[i] = musicinfos[i].split(',');
        // 총 몇분 재생했는 지 계산
        let time =0;
        let h1 = parseInt(musicinfos[i][0].split(':')[0]);
        let m1 = parseInt(musicinfos[i][0].split(':')[1]);
        let h2 = parseInt(musicinfos[i][1].split(':')[0]);
        let m2 = parseInt(musicinfos[i][1].split(':')[1]);
        if (m2>m1){
            time = 60*(h2-h1) + m2-m1;
        }else{
            time = 60*(h2-h1-1) + 60+m2-m1;
        }
        let totalContent = '';
        let musicContent = '';
        let str = musicinfos[i][3];
        // 노래의 음을 새로운 문자열로 변환
        for (let j=0; j<str.length; j++){
            if (j<str.length-1 && str[j+1]==='#'){
                musicContent += KEY[str[j]+'#'];
                j++;
            }else{
                musicContent += KEY[str[j]];
                
            }
        }
        // 재생된 음을 문자열로 생성
        for (let i=0; i<time; i++){
            totalContent += musicContent[i%musicContent.length];
        }
        arr.push({time:time, title:musicinfos[i][2],content:totalContent});
    }
    // newM을 포함한 문자열을 찾기
    for (let i=0; i<arr.length; i++){
        let content = arr[i].content;
        if(content.includes(newM)){
            answerList.push(arr[i]);
        }
    }
    // 없으면 이렇게 반환
    if(answerList.length===0){
        return "(None)";
    }
    // 있으면 time 순으로 정렬
    answerList.sort((a,b)=>{
        if (a.time>b.time){
            return -1;
        }else if (a.time <b.time){
            return 1;
        }else{
            return 0;
        }
    })
    // 첫 번째의 제목 반환
    answer = answerList[0].title;
    return answer;
}

복기

  1. 처음에 m과 musicinfos의 악보 정보 문자열의 모든 문자를 #이 존재하지 않는 문자로 변환하지 않고 코드를 작성했다. 정답은 나왔지만 코드를 작성하는데 너무 오래 걸렸다. #이 포함되면 문자열의 includes 메서드를 쓸 수 없다. includes 메서드를 사용하지 않고 코드를 작성하니 어려웠다.
  2. 나중에 사용할 메서드가 사용 가능한지 사전에 체크를 미리 하는 연습을 해야 한다.