ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 기초적인 정규 표현식 이해하기
    JavaScript 2021. 10. 10. 23:25

    개발에 발을 담근(?) 이후 정규 표현식에 대해 들어본적은 많으나 직접 사용해본 적은 한번도 없었다.

    알고리즘 문제를 풀때 가끔 정규표현식을 사용하는 사람을 보고 '오 이게 대체 뭐지~ 머리아프다' 하고 지나만 갔다.

    하지만 회사 동료의 설명을 잠깐 듣고 나니, 이참에 한번 공부해보자 싶어서 정리해본다.

     

    (설명은 자바스크립트를 기반으로 했습니다)


    정규 표현식과 플래그

    두 슬래시(/) 사이에 글자를 써넣어서 정규 표현식을 작성할 수 있다.

    정규식 관련 메서드로는 match, test, replace 등이 있다 (여기서 replace는 생략함)

     

    test : test 이후 오는 문자열이 regExp와 일치하는지 true/false 를 반환받는다.

    match : 문자열에서 regExp 와 일치하는 것들을 찾아내서 반환받는다.

    let regExp = /헬로월드/
    alert(regExp.test("헬로월드")) // true
    
    alert("헬로월드".match(regExp)) // 헬로월드

    검색에 영향을 주는 플래그는 6개가 존재한다. 플래그는 여러가지를 합쳐서 쓸 수 있다.

    • - 대소문자 구분 없이 검색
    • g  - 패턴과 일치하는 모든 것들을 찾음. g 플래그가 없으면 일치하는 첫번째 결과만 반환
    • m - 다중 행 모드를 활성화. 다음 행에 오는 문자를 패턴의 첫 문자로 인식함 (^을 쓸 경우 다중 행 모드가 없으면 문자열 첫 시작 이후론 첫 문자로 인식하지 않음)
    • s - . 이 개행문자 \n 도 포함하도록 함
    • u - 유니코드 전체를 지원
    • y - 문자 내 특정 위치에서 검색을 진행하는 'sticky'모드 활성화
    let str = "Java JavaScript Python";
    alert( str.match(/java/) ); // null
    alert( str.match(/java/i) ); // Java
    alert( str.match(/java/gi) ); // Java, Java

     

    [ ] : 후보군이자 범위

    • [ ] 안에 있는 글자들은 or 로 이어져서, 그 중 한 문자가 들어가 있으면 일치하는 것으로 판단한다.
    alert("classA".match(/class[ABC]/g)); // classA
    alert("class".match(/class[ABC]/g));  // null -> A,B,C 셋 중 하나가 있어야함
    • [ ] 안에 - 를 사용해서 범위를 표현할 수 있다
    alert("classA".match(/class[A-Z]/g)); // classA
    alert("class1A".match(/class[0-9A-Z]/g)); // class1 -> 0~9, A~Z 중 하나
    alert("class다".match(/class[가-힣]/g)); // class다 -> 한글도 된다!
    
    // - 자체를 찾으려면 escape(\) 사용
    alert("class-A".match(/class[A-Z\-]A/g)); // class-A
    • [^..] 로 여집합을 표현할 수 있다
    alert("classA".match(/class[^BC]/g)); // classA -> B,C 제외라 일치
    alert("classB".match(/class[^BC]/g)); // null
    • 아래와 같이 간략하게 표현하는 것도 가능하다
      • \d : 어떤 하나의 숫자 = [0-9]  
      • \w : 어떤 하나의  문자 = [a-zA-Z0-9_]
      • \s : 공백 하나 = [\t\n\v\f\r]
      • \D : \d의 여집합 = [^0-9]  
      • \W : \w의 여집합 = [^a-zA-Z0-9_]
      • \S : \s의 여집합 = [^\t\n\v\f\r]

     

    자주 등장하는 표현식들

    표현식 설명
    (x) 소괄호로 문자를 묶어서 그룹으로 사용
    x{n} x가 n번 반복됨
    x{n,} x가 n번 이상 반복됨
    x{n,m} x가 최소 n번 이상, 최대 n번 이하 반복됨
    x* x가 0번 이상 반복됨
    x+ x가 1번 이상 반복됨
    x? x가 있거나 없음(0번 or 1번)
    ^x x로 시작함
    x$ x로 끝남

     


    고객 휴대폰 번호 입력 받기

    프로젝트에 정규식이 들어간 코드가 딱 두 개가 있어서 확인을 해봤다.

    기존 프로젝트 코드에 들어가 있는 휴대폰 번호 정규식은 아래와 같았다.

    /^(01[0-9]{1})[0-9]{3,4}[0-9]{4}$/

    앞에서부터 차근차근 풀이하자면

    ^(01[0-9]{1}) : 010 ~ 019 까지의 세 문자가 한 번 반복되는걸로 문자열이 시작된다 (ex. 010)

    [0-9]{3,4} : 숫자3번 이상, 4번 이하로 반복된다 (ex. 123)

    [0-9]{4}$ : 숫자4번 반복된 후 문자열이 끝난다 (ex. 4567)

     

    굳이 여기서 [0-9]를 안쓰고, \d로 써도 결과는 같다.

    /^(01\d{1})\d{3,4}\d{4}$/

     

    위 정규 표현식을 사용할 경우 누군가 010-9999-9999 를 입력한다면 올바르지 않은 휴대폰번호로 인식할 것이다.

    -를 쓰고 안쓰더라도 영향을 안주고싶다면 ? 를 사용하면 된다.

    /^(01\d{1})-?\d{3,4}-?\d{4}$/

     

    고객 출생년도 입력받기

    두 번째 코드는 출생년도를 입력받는 코드다. 

    /^(19[0-9][0-9]|20\d{2})$/

    짧은 식이라 위 전화번호를 읽었다면 쉽게 이해할 수 있다.

    19xx 년으로 표시되거나 20xx 년으로 표시된다면 유효한 출생년도로 인정해주고 있다. (|는 or 연산자로 사용된다)

    [0-9]를 또 \d로 바꾸면 아래와 같다.

    /^(19\d{2}|20\d{2})$/

    이렇게 고치고 보니 더 간결해질 수 있겠다 싶어서 아래처럼 만들었다.

    /^(19|20)\d{2}$/

     

    이메일 입력받기

    기존 코드에는 없지만, 만약 유효한 이메일을 입력받으려면 어떻게 해야할까?

    이건 어떤 형태가 올바른 이메일이냐에 대한 결정에 따라서 다양한 답이 나올 수 있을 것 같다.

    ^[A-Za-z0-9](\w|[.-])*@[A-Za-z0-9](\w|[.-])*\.(com|co.kr)$

    위는 내가 생각해본 답이다. 생각한 조건은 아래와 같다.

     

    1. 아이디와 도메인명의 시작은 [A-Za-z0-9] 가 허용된다 (\w를 쓰고 싶었으나 \w에는 _가 포함되어 있다ㅜㅜ)

    2. 아이디와 도메인명의 시작 외 나머지 부분은 전체 문자(\w) 및 . - 가 올 수 있다

    3. 아이디와 도메인명 사이에는 @ 가 있다

    4. .com 혹은 .co.kr 로 끝난다

     

     

     

     

    아래 링크에서 정규 표현식을 쉽게 테스트해볼수 있다

    https://regexr.com/

    'JavaScript' 카테고리의 다른 글

    [html] 웹페이지에 네이버 지도 넣기 (NAVER Map API)  (0) 2021.12.05
    DOM 이란?  (0) 2021.11.21
    호이스팅(Hoisting)이란?  (0) 2021.11.07

    댓글

Designed by Tistory.