ComputerScience/알고리즘

Python 정규표현식(regex) 정리하기 - 1

Roothyo 2022. 2. 22. 17:40

정규 표현식(Regular Expressions)은 복잡한 문자열을 처리할 때 사용하는 기법으로, 파이썬만의 고유 문법이 아니라 문자열을 처리하는 모든 곳에서 사용된다.

정규 표현식의 기초, 메타 문자

정규 표현식에서 사용되는 메타 문자는 다음과 같은 것이 있다.

 

1. 문자 클래스 [] : "[] 사이의 문자들과 매치". [abc] 라면 a, b, c 중 한개의 문자와 매치를 뜻한다. 두 문자 사이에 "-" 를 사용하면 두 문자 사이의 범위(From-To)를 의미한다. [0-5]는 [012345]와 동일하다. 문자 클래스 안에는 어떤 문자나 메타 문자도 사용할 수 있지만 ^를 조심하여야 한다. ^는 반대라는 의미를 갖고 있어 [^0-9]라는 정규 표현식은 숫자가 아닌 문자만 매치된다.

 

- [a-zA-Z] : 알파벳 모두

- [0-9] : 숫자

자주 사용하는 정규식은 별도의 표기법으로 표현할 수 있다. 
- \d : [0-9]와 동일한 표현식
- \D : 숫자가 아닌 것과 매치. [^0-9]와 동일한 표현식
- \s : whitespace 문자와 매치, [ \t\n\r\f\v]와 동일한 표현식이다.
- \S : whitespace 문자가 아닌 것과 매치. [^ \t\n\r\f\v]와 동일한 표현식이다.
- \w : 문자+숫자와 매치, [a-zA-Z0-9_]와 동일한 표현식이다.
- \W : 문자 + 숫자가 아닌 문자와 매치. [^a-zA-Z0-9_]와 동일한 표현식이다.

 

2. Dot . : "줄바꿈 문자인 \n을 제외한 모든 문자와 매치됨을 의미함". a.b는 "a + 모든문자 + b"의 의미이다. a[.]b 는 "a.b"문자열과 매치되고, "a0b"등의 문자열과는 매치되지 않는다. 문자클래스 내에 메타문자가 사용된다면 문자 그대로를 의미하므로 주의할 것.

 

3. 반복 * : " * 은 바로 앞에 있는 문자가 0부터 무한대로 반복될 수 있다는 의미이다."

 

예를 들어 정규표현식이 "ca*t"이라면

  • ct
  • cat
  • caaat

문자열이 모두 매치된다.

 

4. 반복 + : +는 최소 1번 이상 반복될 때 사용된다. 즉 * 가 반복 횟수가 0부터라면+는 반복 횟수 1부터인 것이다.

예를 들어 "ca+t"라면 "ct"는 매치가 안되지만, "cat", "caaat"는 매치가 되는 것을 볼 수 있다.

 

5. 반복 {m, n}, ? : {} 메타문자를 사용하면 반복 횟수를 고정할 수 있다.

  • {m} 은 반드시 m번 반복
  • {m, n}은 m이상 n 이하 반복
  • {m, }은 m 이상 반복
  • {,m}은 m 이하 반복
  • ? : 반복은 아니지만 {0, 1}의 있어도 되고 없어도 되는 뜻을 의미한다.

파이썬에서 정규표현식을 지원하는 re 모듈

파이썬은 정규 표현식을 지원하기 위해 re(regular expression )모듈을 제공한다. re 모듈은 파이썬을 설치할 때 자동으로 설치되는 기본 라이브러리로 다음과 같은 4가지 메서드를 제공한다.

Method 목적
match() 문자열의 처음부터 정규식과 매치되는지 조사한다.
search() 문자열 전체를 검색하여 정규식과 매치되는지 조사한다.
findall() 정규식과 매치되는 모든 문자열(substring)을 리스트로 돌려준다.
finditer() 정규식과 매치되는 모든 문자열(substring)을 반복 가능한 객체로 돌려준다.

우선 다음과 같은 패턴을 통해 메소드들이 어떻게 동작하는지 볼 수 있다.

import re
p = re.compile("[a-z]+")
m = p.match("python")
print(m)
<re.Match object; span=(0, 6), match='python'>

m = p.match("3 python")
print(m)
None

m = p.search("3 python")
print(m)
<re.Match object; span=(2, 8), match='python'>

result = p.findall("life is too short")
print(result)
['life', 'is', 'too', 'short']

result = p.finditer("life is too short")
print(result)
<callable_iterator object at 0x000001E9CF059B20>

for r in result: print(r)
<re.Match object; span=(0, 4), match='life'>
<re.Match object; span=(5, 7), match='is'>
<re.Match object; span=(8, 11), match='too'>
<re.Match object; span=(12, 17), match='short'>

Match object의 메소드에는 group, start, end, span의 메서드들을 통해서 객체를 알아볼 수 있다.

 

컴파일 옵션

정규식을 컴파일할 때 다음 옵션을 사용할 수 있다.

  • DOTALL(S) - . 이 줄바꿈 문자를 포함하여 모든 문자와 매치할 수 있도록 한다.
  • IGNORECASE(I) - 대소문자에 관계없이 매치할 수 있도록 한다.
  • MULTILINE(M) - 여러줄과 매치할 수 있도록 한다. 
  • VERBOSE(X) - verbose모드를 사용할 수 있도록 한다.

옵션을 사용할 때는 re.DOTALL이라고 써도되고 re.S처럼 약어를 써도 된다.

 

import re

p = re.compile('a.b')
m = p.match("a\nb")
print(m)

p = re.compile('a.b', re.DOTALL)
m = p.match("a\nb")
print(m)

p = re.compile('[a-z]+', re.I)
p.match('python')
p.match('Python')
p.match('PYTHON')

p = re.compile("^python\s\w+")
print(p.findall(data))
data = """python one
life is too short
python two
you need python
python three"""
p = re.compile("^python\s\w+", re.MULTILINE)
print(p.findall(data))

charref = re.compile(r"""
 &[#]                # Start of a numeric entity reference
 (
     0[0-7]+         # Octal form
   | [0-9]+          # Decimal form
   | x[0-9a-fA-F]+   # Hexadecimal form
 )
 ;                   # Trailing semicolon
""", re.VERBOSE)

 

 

 

[참조 : 위키독스 점프 투 파이썬 (https://wikidocs.net/4308)]