1. 왜 정규표현식이 필요할까?
- 기본적으로 BeautifulSoup의 find(), find_all(), select() 등을 쓰면 정해진 태그와 속성에 따라 데이터를 가져올 수 있다.
- 하지만,
i) 정확한 문자열이 아니라 패턴으로 데이터를 찾거나,
ii) 부분 일치 / 유동적인 텍스트 / 숫자 포함 여부 등을 찾고 싶다면,
- 정규표현식을 사용한다면 쉽게 찾을 수 있다.
- 파이썬에선 re module로 쉽게 활용가능하다.
2. 정규표현식을 BeautifulSoup에서 쓰는 방법
- re 모듈을 활용하면 다음 항목에서 정규표현식 사용이 가능하다.
"""
i) name : 태그 이름이 특정 패턴과 일치하는 경우
ii) text : 텍스트 내용이 패턴과 일치하는 경우
iii) attrs : 속성 값이 특정 패턴을 따를 때
"""
import re
from bs4 import BeautifulSoup
3. Example
- 다음과 같은 HTML 코드가 있다고 가정해보자.
html = '''
<html>
<body>
<h1>Python Tutorial</h1>
<p class="content">Welcome to Python</p>
<p class="content">Learn more about Data Science</p>
<a href="/article/123">Article 123</a>
<a href="/article/456">Article 456</a>
<a href="/about">About Us</a>
</body>
</html>
'''
soup = BeautifulSoup(html, 'html.parser')
- 여기서 특정 텍스트("Python")이 포함된 태그를 찾는다면 다음과 같이 찾을 수 있다.
import re
results = soup.find_all(text=re.compile('Python'))
for r in results:
print(r)
------------------------------------------------
Output
Python Tutorial
Welcome to Python
- text = re.compile()은 텍스트 내용을 대상으로 정규표현식을 적용할 수 있게 해준다.
- href에서 /article로 시작하는 attribute를 찾고싶다면 다음과 같이 할 수 있다.
links = soup.find_all('a', href=re.compile('^/article/'))
for link in links:
print(link['href'])
----------------------------------------------------------------
Output
/article/123
/article/456
- '^STRING' 여기서 ^는 STRING으로 시작하는 text를 다 찾아준다.
- 이러한 정규표현식을 키에 적용도 가능하다.
# 태그 이름이 'h'로 시작하는 모든 태그 찾기
headers = soup.find_all(re.compile('^h'))
for h in headers:
print(h.name, h.text)
h1 Python Tutorial
- 뿐만 아니라, content가 class인 아이들도 추출가능하다.
# class가 content로 끝나는 태그 찾기
content_tags = soup.find_all('p', class_=re.compile('content$'))
for tag in content_tags:
print(tag.text)
Welcome to Python
Learn more about Data Science
4. 정규표현식을 이용하여 email을 추출
- 정규표현식은 문자열에서 특정한 패턴을 찾아내기 위한 강력한도구이다.
- Web Scraping할 때, 특정 데이터(이메일, 날짜, 숫자 등)을 추출할 때 매우 유용하게 쓰인다.
re.findall(r'\d+', '총 1,234명이 참여했습니다') # ['1', '234']
- 이를 이용하여 이메일 주소를 추출해보자.
- 일반적인 이메일 주소의 포맷은 다음과 같은 형태다.
[\w\.-]+@[\w\.-]+\.\w+
re.findall(r'[\w\.-]+@[\w\.-]+\.\w+', '문의: hello@example.com')
# ['hello@example.com']
- 전화번호는 다음과 같다.
re.findall(r'01[0-9]-\d{3,4}-\d{4}', '문의는 010-1234-5678로 주세요')
- 날짜는 다음과 같다.
'DS Study > Web Scraping' 카테고리의 다른 글
[Web Scraping][3.3] lambda Expressions (0) | 2025.03.26 |
---|---|
[Web Scraping] [3.1] BeautifulSoup (HTML Parsing) (0) | 2025.03.26 |
[Web Scraping] [2.2] Introduction to BeautifulSoup (0) | 2025.03.25 |
[Web Scraping] [2.1] urllib (파이썬 라이브러리) (0) | 2025.03.25 |
[Web Scraping] [1.2] HTML,CSS (0) | 2025.03.24 |