20437. 문자열 게임 2 - node.js / javascript

윤상준·2022년 7월 1일
0

BOJ - node.js / javascript

목록 보기
54/55
post-thumbnail

문제

내 코드

let fs = require("fs");
let input = fs.readFileSync("/dev/stdin").toString().trim().split("\n");

function solution(input) {
    const T = Number(input[0]);
    input = input.slice(1).reverse();
    const answer = [];

    while (input.length) {
        const W = input.pop().split("");
        const K = Number(input.pop());
        const words = Array.from(new Set(W));
        const candidates = {};
        let lenList = [];

        for (let word of words) {
            let temp = [];
            for (let i = 0; i < W.length; i++) {
                if (W[i] === word) temp.push(i);
            }
            if (temp.length >= K) {
                candidates[word] = temp;
            }
        }

        if (!Object.keys(candidates).length) {
            answer.push(-1);
            continue;
        } else {
            for (let alpha in candidates) {
                const current = candidates[alpha];

                if (current.length === K) {
                    let firstIdx = current[0];
                    let lastIdx = current[K - 1];
                    lenList.push(lastIdx - firstIdx + 1);
                } else {
                    for (let i = 0; i < current.length - K + 1; i++) {
                        lenList.push(current[i + K - 1] - current[i] + 1);
                    }
                }
            }
        }
        answer.push(`${Math.min(...lenList)} ${Math.max(...lenList)}`);
    }
    return answer.join("\n");
}

console.log(solution(input));

깃허브 링크

https://github.com/highjoon/Algorithm/blob/master/BOJ/20437.js

풀이

문자 후보군을 추려내기 위해 W를 Set로 한번 정제한다.
후보군을 돌면서 찾는 문자와 일치하는 문자의 인덱스를 배열에 저장한다.
그 배열의 길이가 K 이상이면 일단 통과. => candidates 객체에 저장한다. (key: 문자, value: 인덱스 배열)
그럼 이렇게 모아진다.

{ u: [ 1, 7 ], r: [ 4, 11 ], a: [ 5, 8, 13 ], o: [ 10, 15 ] }

객체가 비어있다면 만족하는 연속 문자열이 없는 경우 이므로 -1을 넣는다.
객체에 요소가 들어있다면 길이가 K 이상인 문자열이 적어도 하나 이상 있다는 의미.

이제 객체를 돌면서 문자열 길이가 K와 같으면 바로 lastIdx - firstIdx + 1 즉, 길이를 계산한다.
길이가 K보다 크면 각각의 문자열 길이를 구해야한다.

더 정확히는 객체의 각 문자를 정확히 K개 포함하면서 첫 번째와 마지막 글자가 모두 해당 문자로 같은 연속 문자열의 길이를 의미.

for (let i = 0; i < current.length - K + 1; i++) {
  lenList.push(current[i + K - 1] - current[i] + 1);
}

이렇게 계산한 길이는 모두 배열 lenList에 넣는다.

이후 lenList에서 최솟값, 최댓값을 구하면 된다.

profile
하고싶은건 많은데 시간이 없다!

0개의 댓글