본문으로 건너뛰기
2022. 9. 14·약 3분

자바스크립트 정규표현식: 수량자와 탐욕·지연 매칭 | Part 2

별표가 얹힌 흰 카드 뒤로 파란 카드가 작고 옅어지며 이어지고 점 셋이 뒤따르는 그림

문자 반복 횟수 지정하기​

1) +​

앞의 요소가 한 번 이상 반복될 때 일치합니다.

2) ?​

앞의 요소가 없거나 한 번 나타날 때 일치합니다.

3) *​

앞의 요소가 없거나 여러 번 반복될 때 일치합니다.


빈 문자열 일치와 무한 루프​

/[a-z]*/g;

위 패턴은 알파벳이 없는 위치에서도 빈 문자열과 일치합니다. 반면 /s[a-z]*/g는 앞의 s가 반드시 필요하므로 빈 문자열과 일치하지 않습니다. 길이 0인 결과가 나올 수 있는 g 플래그 정규식을 exec 반복문에서 사용하면 lastIndex가 전진하지 않아 무한 루프가 생길 수 있습니다. 오류를 던지지 않고 반복만 멈추지 않으므로 주의해야 합니다.


탐욕적 매칭과 지연 매칭​

수량자는 기본적으로 전체 패턴이 성립하는 범위에서 가능한 한 많은 문자를 소비합니다. 이를 탐욕적(greedy) 매칭이라고 합니다.

1) 탐욕적 매칭​

아래 문자열에서는 <p>.*<\/p>와 <p>.+<\/p>가 마지막 </p>까지 한꺼번에 선택합니다.

탐욕 매칭 패턴이 두 문단을 한 덩어리로 통째 선택한 화면

2) 지연 매칭​

/<p>.*?<\/p>/처럼 수량자 뒤에 ?를 붙이면 가능한 한 적게 소비합니다. 따라서 첫 번째 </p>에서 일치를 멈춥니다. 이 예제는 매칭 차이를 보여주기 위한 것이며, 실제 HTML 구조를 해석할 때는 HTML 파서를 사용해야 합니다.

지연 매칭 패턴이 첫 p 태그 하나에서 멈춘 화면


반복 횟수 범위 지정하기​

1) {min,max}​

앞의 요소가 min번 이상 max번 이하 반복될 때 일치합니다.

2) {min}​

앞의 요소가 정확히 min번 반복될 때 일치합니다.

3) {min,}​

앞의 요소가 min번 이상 반복될 때 일치합니다.

예제​

다음 패턴은 연속된 단어 문자(\w) 3개 이상 5개 이하와 일치합니다.

/\w{3,5}/g;

다음 패턴은 단어 문자 한 개 뒤에 단어 문자 3개 이상 5개 이하가 이어진, 총 4~6개의 문자와 일치합니다.

/\w\w{3,5}/g;

다음 패턴은 연속된 단어 문자 3개와 일치합니다.

/\w{3}/g;

다음 패턴은 단어 문자 3개 뒤에 하이픈이 오는 문자열과 일치합니다.

/\w{3}-/g;

다음 패턴은 연속된 단어 문자 3개 이상과 일치합니다.

/\w{3,}/g;

다음 패턴은 # 뒤에 대문자 16진수 숫자 6개가 오는 부분과 일치합니다. 소문자도 허용하려면 i 플래그를 추가합니다.

/#[0-9A-F]{6}/g;

다음 패턴은 미국 사회보장번호(SSN)의 3자리-2자리-4자리 형식과 일치합니다. 번호가 실제로 발급됐는지까지 검증하지는 않습니다.

/\d{3}-\d{2}-\d{4}/g;

수량자 뒤에 붙는 물음표​

수량자는 기본적으로 가능한 한 많이 반복합니다. 뒤에 ?를 붙이면 전체 패턴이 성립하는 범위에서 가능한 한 적게 반복합니다.

?는 단독으로 쓰이면 앞의 요소를 0회 또는 1회 반복하는 수량자입니다. *, +, {n,m} 같은 수량자 뒤에 붙으면 해당 수량자를 지연(lazy) 방식으로 바꿉니다. 아래는 선택적인 국가 코드와 세 자리 지역 번호를 가진 전화번호 형식을 검사하는 연습 예제입니다. 실제 국가별 전화번호 유효성까지 검증하지는 않습니다.

const phone = document.getElementById("phone");
const regPhone = /^(?:\+\d{1,3}[ .-]?)?(?:\(\d{3}\)|\d{3})[ .-]?\d{3}[ .-]?\d{4}$/;

phone.addEventListener("keyup", (e) => {
console.log(e.target.value);
if (regPhone.test(e.target.value)) {
phone.classList.remove("red");
phone.classList.add("green");
} else {
phone.classList.add("red");
phone.classList.remove("green");
}
});
좋은 사람들과 재미있는 일을 하며 열정적이고 즐겁게 살고 싶은 개발자