본문 바로가기
Developer/Algorithm

프로그래머스 코딩테스트 연습 Level 2 - 괄호 회전하기 (JavaScript)

by 김씩씩 2022. 8. 8.

프로그래머스 코딩테스트 연습 Level 2 - 괄호 회전하기 (JavaScript)

 

Programmers(프로그래머스)의 코딩테스트 연습문제 Level 2 중,

[괄호 회전하기] 문제를 JavaScript를 사용하여 해결해 보도록 하겠습니다.

 

문제

문제 설명

다음 규칙을 지키는 문자열을 올바른 괄호 문자열이라고 정의합니다.

  • (), [], {} 는 모두 올바른 괄호 문자열입니다.
  • 만약 A가 올바른 괄호 문자열이라면, (A), [A], {A} 도 올바른 괄호 문자열입니다. 예를 들어, [] 가 올바른 괄호 문자열이므로, ([]) 도 올바른 괄호 문자열입니다.
  • 만약 A, B가 올바른 괄호 문자열이라면, AB 도 올바른 괄호 문자열입니다. 예를 들어, {} 와 ([]) 가 올바른 괄호 문자열이므로, {}([]) 도 올바른 괄호 문자열입니다.

대괄호, 중괄호, 그리고 소괄호로 이루어진 문자열 s가 매개변수로 주어집니다. 이 s를 왼쪽으로 x (0 ≤ x < (s의 길이)) 칸만큼 회전시켰을 때 s가 올바른 괄호 문자열이 되게 하는 x의 개수를 return 하도록 solution 함수를 완성해주세요.

 

제한사항

  • s의 길이는 1 이상 1,000 이하입니다.

 

입출력 예

s result
"[](){}" 3
"}]()[{" 2
"[)(]" 0
"}}}" 0

 

입출력 예 설명

입출력 예 #1

  • 다음 표는 "[](){}" 를 회전시킨 모습을 나타낸 것입니다.
x s를 왼쪽으로 x칸만큼 회전 올바른 괄호 문자열?
0 "[](){}" O
1 "](){}[" X
2 "(){}[]" O
3 "){}[](" X
4 "{}[]()" O
5 "}[](){" X
  • 올바른 괄호 문자열이 되는 x가 3개이므로, 3을 return 해야 합니다.

입출력 예 #2

  • 다음 표는 "}]()[{" 를 회전시킨 모습을 나타낸 것입니다.
x s를 왼쪽으로 x칸만큼 회전 올바른 괄호 문자열?
0 "}]()[{" X
1 "]()[{}" X
2 "()[{}]" O
3 ")[{}](" X
4 "[{}]()" O
5 "{}]()[" X
  • 올바른 괄호 문자열이 되는 x가 2개이므로, 2를 return 해야 합니다.

입출력 예 #3

  • s를 어떻게 회전하더라도 올바른 괄호 문자열을 만들 수 없으므로, 0을 return 해야 합니다.

입출력 예 #4

  • s를 어떻게 회전하더라도 올바른 괄호 문자열을 만들 수 없으므로, 0을 return 해야 합니다.

 

 

작성한 답

solution.js

function solution(s) {
    const bracket = { '(': ')', '[': ']', '{': '}' }
    const bracketLeft = Object.keys(bracket);
    
    return s.split('').reduce((ac, v, i) => {
        const curStr = s.slice(i) + s.slice(0, i);
        const stack = [];
        for (const curChar of curStr) {
            if (bracketLeft.includes(curChar)) stack.push(curChar)
            else {
                if (bracket[stack.pop()] !== curChar) return ac;
            }
        }
        return stack.length === 0 ? ++ac : ac;
    }, 0);
}

 

설명

먼저 bracket 변수에 object 형으로 괄호 종류에 따라 짝을 바로 알 수 있도록 합니다.

그리고 bracket object에서 key 값만 따로 빼와 왼쪽 괄호만을 가지고 있는 array 변수 bracketLeft를 하나 만들어둡니다.

 

변수를 미리 하나 생성해두고 반복문을 돌며 조건이 맞을 때 마다 해당 변수를 1씩 증가시켜 답을 만들어내도 되지만,

저는 reduce를 사용하여 해결하였습니다.

 

문자열 s를 split('')을 사용하여 배열로 만든 뒤, reduce를 사용하여 s의 길이만큼 반복합니다.

curStr 변수에 s를 왼쪽으로 i칸만큼 회전한 문자열을 담아주고,

올바른 괄호 문자열인지를 확인하기 위해 stack으로 사용할 변수 stack을 빈 배열로 선언합니다.

curStr을 한 문자씩 반복하며 현재의 문자가 barcketLeft 변수 안에 존재하는지 확인하는 것으로 왼쪽 괄호인지 확인하고,

왼쪽 괄호라면 stack에 포함시키고,

그렇지 않다면 stack.pop() 를 사용하여 마지막에 넣은 왼쪽 괄호를 꺼내고

bracket 변수에서 마지막 넣은 왼쪽 괄호에 해당하는 오른쪽 괄호가 현재 문자(괄호)와 같은지 체크하여

같지 않다면 누적값(ac), 즉 올바른 괄호 문자열이 되는 횟수를 현재 그대로 반환합니다.

반복문이 끝났지만 stack에 남아있는 왼쪽 괄호가 있다면 올바른 괄호 문자열이 아닌 것이므로 ac를 그대로 반환하고,

그렇지 않다면 ac를 1 증가시킨 뒤 반환하여 올바른 괄호 문자열이 되는 횟수를 증가시킵니다.

 

위 과정을 거쳐 reduce가 반환하는 값은 최종적으로 올바른 괄호 문자열이 되는 횟수이므로,

해당 값을 반환하는 것으로 문제를 해결할 수 있습니다.

 

 

 

도움이 되셨다면 공감, 댓글 부탁드립니다!

궁금하신 점이나 요청사항은 언제든지 말씀해주세요!

피드백도 언제나 환영입니다!

 

감사합니다.


댓글