웹 페이지의 html 문서를 가져오는 건 쉽다
python 라이브러리인 requests를 사용하면 f12를 누르면 나오는 elements 탭의 내용을 긁어올 수 있다
예를 들어서 tistory가 서비스하는 kakao의 검색 엔진(?)인 daum.net의 웹 페이지를 가져오려면 다음과 같다.
r.text에 웹 페이지가 있고 str type으로 저장된다.
import requests
def read_webpage(link):
print('read webpage')
r = requests.get(link)
print(f'status code : {r.status_code}')
if r.status_code == requests.codes.ok:
return r.text
else:
r.raise_for_status()
html_text = read_webpage('https://www.daum.net/')
하지만 원하는 데이터를 가져오는 방법은 여러가지다.
1. python str의 find를 사용해서 index를 알아내서 원하는 데이터 위치를 출력하거나
2. bs4의 beautifulsoup을 사용해 HTML tag, class 속성 기준으로 원하는 데이터를 찾을 수 있다.
원하는 데이터를 실시간 검색어라고 해보자
다음의 경우 검색창 밑에 실시간 검색어가 뜬다
<a href="https://search.daum.net/search?w=tot&q=%EC%97%8" class="link_favorsch @7">엄정화 컴백확정</a>
a tag로 링크 연결이 되어있고 class로는 link_favorsch와 @7, 텍스트 내용은 '엄정화 컴백확정' 이다.
link_favorsch를 찾아보면 실시간 검색어 태그는 다 이거로 되어있다
1. str.find() 사용
여기서 텍스트 내용인 '엄정화 컴백확정'을 가져오기 위해서
1) class="link_favorsch @인 부분의 위치를 찾고(index 변수)
2) index부터 시작해서 >의 위치를 찾아 텍스트 내용 시작 위치를 찾고(start 변수)
3) start부터 시작해서 </a>의 위치를 찾아 텍스트 내용 끝 위치를 찾는다(end 변수)
이걸 코드로 나타내면 다음과 같다
str.find()로 문자열을 못찾으면 -1을 반환하기 때문에 while문 종료를 이걸로 설정한다.
def find_something(text, sth):
print(f'find {sth}')
start = 0
while text.find(sth, start) != -1:
index = text.find(sth, start) # 1)
start = text.find(">", index) # 2)
end = text.find('</a>', start) # 3)
print(text[start+1:end])
find_something('class="link_favorsch @', html_text)
2. bs4의 BeautifulSoup 사용
BeautifulSoup도 find()처럼 str을 읽고 그걸 html.parser를 돌려서 태그를 나누기 때문에
requests의 결과(html_text)를 그대로 사용한다.
BeautifulSoup의 select()를 사용해서 tag 이름과 class 속성을 알면 텍스트 내용은 .text로 쉽게 알 수 있다
어떻게 보면 str.find()를 사용하는 것보다 쉽고 눈에 잘 들어오는 것 같다
** search_something 함수를 수정했다.
tag 하나에 classname이 여러 개 있을 때 classname 여러 개 모두에 부합하는 텍스트를 찾도록 수정해보았다.
python * 연산자를 사용해서 '가변 인자'라는 걸 사용할 수 있는데 꽤 유용해보였다
def search_something(text, tagname, *classname):
print(f'search with bs4 : {classname}')
soup = BeautifulSoup(text, 'html.parser')
classname_str = '.'.join(classname)
print(f'{tagname}.{classname_str}')
return [tag.text.replace('\n\n\n','\n') for tag in soup.select(f'{tagname}.{classname_str}')]
list_favorsch = search_something(html_text, 'ul','list_favorsch')
코드는 아래 URL에 공개해두었다
github.com/ny0011/ai_mini_project
'개발 > Python' 카테고리의 다른 글
[codility] MaxCounters (0) | 2021.02.17 |
---|---|
selenium으로 웹 정보를 스크랩해보자 (0) | 2020.08.31 |
댓글