본문 바로가기
Algorithms/코테 문풀

[프로그래머스] 옹알이(1) - JavaScript / 정규 표현식 활용

by hi-rachel 2023. 1. 13.

✏️ 문제 설명

머쓱이는 태어난 지 6개월 된 조카를 돌보고 있습니다. 조카는 아직 "aya", "ye", "woo", "ma" 네 가지 발음을 최대 한 번씩 사용해 조합한(이어 붙인) 발음밖에 하지 못합니다. 문자열 배열 babbling이 매개변수로 주어질 때, 머쓱이의 조카가 발음할 수 있는 단어의 개수를 return하도록 solution 함수를 완성해주세요.


제한사항
  • 1 ≤ babbling의 길이 ≤ 100
  • 1 ≤ babbling[i]의 길이 ≤ 15
  • babbling의 각 문자열에서 "aya", "ye", "woo", "ma"는 각각 최대 한 번씩만 등장합니다.
    • 즉, 각 문자열의 가능한 모든 부분 문자열 중에서 "aya", "ye", "woo", "ma"가 한 번씩만 등장합니다.
  • 문자열은 알파벳 소문자로만 이루어져 있습니다.

 

입출력 예
babbling result
["aya", "yee", "u", "maa", "wyeoo"] 1
["ayaye", "uuuma", "ye", "yemawoo", "ayaa"] 3

입출력 예 설명

입출력 예 #1

  • ["aya", "yee", "u", "maa", "wyeoo"]에서 발음할 수 있는 것은 "aya"뿐입니다. 따라서 1을 return합니다.

입출력 예 #2

  • ["ayaye", "uuuma", "ye", "yemawoo", "ayaa"]에서 발음할 수 있는 것은 "aya" + "ye" = "ayaye", "ye", "ye" + "ma" + "woo" = "yemawoo"로 3개입니다. 따라서 3을 return합니다.

유의사항
  • 네 가지를 붙여 만들 수 있는 발음 이외에는 어떤 발음도 할 수 없는 것으로 규정합니다. 예를 들어 "woowo"는 "woo"는 발음할 수 있지만 "wo"를 발음할 수 없기 때문에 할 수 없는 발음입니다.

 


 

✏️ 문제 풀이

function solution(babbling) {
    let result = 0;
    
    for (let babyTalk of babbling) {
        if (/(aya|ye|woo|ma)\1+/g.test(babyTalk)) continue;
        
        if (/^(aya|ye|woo|ma)+$/g.test(babyTalk)) {
            result++;
        };
    }
    return result;
}

나는 연속 발음을 같이 세는 것에서 막혀서 다른 사람의 풀이를 참고해 풀었다. 정규표현식에 대한 이해가 부족해서 못푼걸 느꼈다.

 


 

정규표현식?

정규 표현식(regular expression, 간단히 regexp 또는 regex, rational expression) 또는 정규식특정한 규칙을 가진 문자열의 집합을 표현하는 데 사용하는 형식 언어이다.

정규 표현식 발만 담구고 싶다면 => 2022.12.19 - [개발 지식] - 정규표현식(regular expression)이란? + 쉽게 공부하는 사이트

 

📌  기본 개념

주로 패턴(pattern)으로 부르는 정규 표현식은 특정 목적을 위해 필요한 문자열 집합을 지정하기 위해 쓰이는 식이다. 문자열의 유한 집합을 지정하는 단순한 방법은 문자열의 요소나 멤버를 나열하는 것이다. 그러나 문자열의 원하는 집합을 지정하기 위해 사용할 수 있는 더 간결한 방법들이 있다. 이를테면 3개의 문자열 "Handel", "Händel", "Haendel"을 포함하는 집합은 패턴 H(ä|ae?)ndel으로 지정이 가능하며 이러한 패턴은 3개의 문자열을 각각 일치(match)시킨다고 이야기한다.

  • Boolean "or"
    • | 은 여러 항목 중 선택을 하기 위해 구분한다. 이를테면 gray|grey는 "gray" 또는 "grey"와 일치한다.
  • 그룹 묶기(Grouping)
    • ()를 사용하면 연산자의 범위와 우선권을 정의할 수 있다. 이를테면 gray|grey gr(a|e)y는 "gray"나 "grey" 집합을 둘 다 기술하는 동일 패턴이다.
  • 양 지정(Quantification)
? 물음표는 0번 또는 1차례까지의 발생을 의미한다. 이를테면 colou?r는 "color"와 "colour"를 둘 다 일치시킨다.
* 별표는 0번 이상의 발생을 의미한다. 이를테면 ab*c"ac", "abc", "abbc", "abbbc" 등을 일치시킨다.
+ 덧셈 기호는 1번 이상의 발생을 의미한다. 이를테면 ab+c는 "abc", "abbc", "abbbc" 등을 일치시키지만 "ac"는 일치시키지 않는다.
{n} 정확히 n 번만큼 일치시킨다.
{min, } "min"번 이상만큼 일치시킨다.
{min,max} 적어도 "min"번만큼 일치시키지만 "max"번을 초과하여 일치시키지는 않는다.

 

📌 Syntax

POSIX 기본 및 확장 표준 문법

  • . : 문자_ 1개의 문자와 일치한다. 단일행 모드에서는 새줄 문자를 제외한다.
  • () : 하위식_ 여러 식을 하나로 묶을 수 있다.
  • [] : 문자 클래스_ '[' 과 ']' 사이의 문자 중 하나를 선택한다. '-' 기호와 함께 쓰면 범위를 지정할 수 있다.
    • 예) [abc]d =  ad, bd, cd / [1-9] = 1부터 9까지 중 하나를 의미
  • [^] : 부정_ 문자 클래스 안의 문자를 제외한 나머지를 선택한다.
    • 예) [^abc]dad, bd, cd는 포함하지 않고 ed, fd 등을 포함
  • ^ : 처음_ 문자열이나 행의 처음을 의미한다.
  • $ : _ 문자열이나 행의 끝을 의미한다.
  • \n : 일치하는 n번째 패턴_ 일치하는 패턴들 중 n번째를 선택하며, 여기에서 n은 1에서 9 중 하나가 올 수 있다.
  • * : 0회 이상_ 0개 이상의 문자를 포함한다.
    • 예) "a*b""b", "ab", "aab", "aaab"를 포함
  • {m, n} : m회 이상 n회 이하
    • 예) "a{1,3}b"는 "ab", "aab", "aaab"를 포함하지만, "b"나 "aaaab"는 포함하지 않는다.

 

POSIX 확장 문법

  • ? : 0 또는 1회
    • 예) "a?b""b", "ab"를 포함
  • + : 1회 이상
    • 예) "a+b""ab", "aab", "aaab"를 포함하지만 "b"는 포함하지 않음
  • :선택_여러 식 중에서 하나를 선택한다.
    • "abc¦adc"abc와 adc 문자열을 모두 포함

 

(위 문제를 풀 때 사용된 문법은 으로 해놨다)

 

++ 문자 클래스

 

▶ RegExp.prototype.test()

test() 메서드는 정규식과 지정된 문자열 간의 일치하는지(match) 검색을 실행합니다. true나 false를 반환.

test(str)

 

 

참고 사이트

[프로그래머스] 옹알이 (2) - JavaScript

(참고로 문제 지문이 리뉴얼되서 옹알이(1)은 이 풀이로 풀리고 옹알이(2)는 풀리지 않는다)

mdn

wikipedia

 

 

🙂 공부하면서 적는 글입니다. 공감과 피드백 환영합니다.