프로그래머스 파일명 정렬 JavaScript

2023년 2월 22일

프로그래머스 파일명 정렬

문제 풀이

HEAD, NUMBER, TAIL로 구성되어 있는 파일들을 정렬하는 문제, 정렬 규칙으로는

  1. HEAD 부분을 기준으로 사전 순으로 정렬한다. 이때 문자열 비교 시 대소문자 구분을 하지 않는다.
  2. 파일명의 HEAD 부분이 대소문자 차이 외에는 같을 경우, NUMBER의 숫자순으로 정렬한다. 이때 012와 12는 정렬 시에 같은 값으로 처리한다.(0 무시)
  3. HEAD, NUMBER 모두 같으면 원래 입력에 주어진 순서를 유지한다.

정렬하기 전, 함수 splitFileName을 이용해 file을 HEAD, NUMBER, TAIL로 나눈다.

function splitFileName(file): file 이름을 [HEAD, NUMBER, TAIL]로 구분 지어 리턴하는 함수, 구분하는 방법은 NUMBER와 TAIL의 시작 인덱스를 찾아 slice하는 것이다. 이때 TAIL이 빈 문자열인 경우도 생각한다.

  • HEAD는 file의 0번부터 NUMBER의 시작 인덱스 이전 file.slice(0, numberIdx)
  • NUMBER는 TAIL이 빈 문자열일 경우 NUMBER의 시작 인덱스부터 나머지 file.slice(numberIdx), TAIL이 빈 문자열이 아닌 경우 NUMBER의 시작 인덱스부터 TAIL의 시작 인덱스 이전까지 file.slice(numberIdx, tailIdx)
  • TAIL = file.slice(tailIdx)

[HEAD, NUMBER, TAIL]로 구분된 file들 files_split을 규칙에 맞게 정렬한다.
마지막으로 정렬된 files_split(배열)을 문자열로 join("")후 리턴.

solution.js
function solution(files) {
    const answer = [];
    const files_split = [];
    
    files.forEach(file => {
        files_split.push(splitFileName(file));
    });

    files_split.sort((a, b) => {
        const a0 = a[0].toUpperCase();
        const b0 = b[0].toUpperCase();

        if (a0 !== b0) {
            if (a0 < b0) {
                return -1;
            }
            if (a0 > b0) {
                return 1;
            }
            return 0;
        }

        if (a0 === b0) {
            if (a[1] !== b[1]) {
                return a[1] - b[1];
            }
            return 0;
        }
    });

    files_split.forEach(file => {
        answer.push(file.join(""));
    });

    return answer;
}

function splitFileName(file) {
    let numberIdx = -1;
    let tailIdx = -1;
    const numbers = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9'];
    for (let i = 0; i < file.length; i++) {
        if (numbers.includes(file[i]) && numberIdx === -1) {
            numberIdx = i;
        }
        if (numberIdx !== -1 && !numbers.includes(file[i])) {
            tailIdx = i;
            break;
        }
    }
    const HEAD = file.slice(0, numberIdx);
    let NUMBER = '', TAIL = '';
    if (tailIdx === -1) {
        NUMBER = file.slice(numberIdx);
    } else {
        NUMBER = file.slice(numberIdx, tailIdx);
        TAIL = file.slice(tailIdx);
    }

    return [HEAD, NUMBER, TAIL];
}

댓글