-
melon 장르별 탑 50곡 정적 크롤링하기AI, 시각화, 빅데이터 기초 2021. 5. 27. 17:18
1. 멜론 장르 음악에서 각 장르별 url 분석
https://www.melon.com/genre/song_list.htm?gnrCode= 를 유지하며 발라드, 댄스, 랩/힙합 등과 같이 왼쪽부터 시작해서 n번째인 장르는 곧 장르코드가 GN0n00임을 알 수 있다.
ex) 포크/블루스는 8번째이므로 포크/블루스를 클릭했을 때 주소는 https://www.melon.com/genre/song_list.htm?gnrCode=GN0800
그래서 입력한 장르별로 코드를 저장하도록 다음과 같이 코드를 짰다.
while(True): genre = input("음악 장르 입력(발라드, 댄스, 힙합, 알앤비, 인디, 록, 트로트, 포크) : ") count = 0 if genre == "발라드": gnrCode = "GN0100" break elif genre == "댄스": gnrCode = "GN0200" break elif genre == "힙합": gnrCode = "GN0300" break elif genre == "알앤비": gnrCode = "GN0400" break elif genre == "인디": gnrCode = "GN0500" break elif genre == "록": gnrCode = "GN0600" break elif genre == "트로트": gnrCode = "GN0700" break elif genre == "포크": gnrCode = "GN0800" break else: print("장르 입력이 잘못 되었습니다. 다시 입력해주십시오.")
2. url을 통해 raw를 가져오고 html로 바꾼다.
header = {'User-Agent': 'Mozilla/5.0 (Windows NT 6.3; Trident/7.0; rv:11.0) like Gecko'} melon_url = "https://www.melon.com/genre/song_list.htm?gnrCode=" + gnrCode raw = requests.get(melon_url, headers = header) soup = BeautifulSoup(raw.text, "html.parser")
멜론은 header가 필요했다.
그래서 requests.get의 두 번째 인자에 headers에 지정한 헤더를 넣어줬다.
3. html 태그를 통해 원하는 정보를 find 계열 함수로 찾아 출력한다.
-> <tbody>에 장르별 인기 노래가 나열되어 있다.
-> 그중 class가 ellipsis rank01인 태그에 각 노래 제목이 있다.
-> class가 ellipsis rank02인 태그에 각 가수 이름이 있다.
그 모든 나열된 값들을 zip으로 모아 노래와 제목을 같이 출력한다.
순위도 출력하고 싶으므로 count 변수를 만들어 루프를 돌 때마다 +1를 하도록 한다.
그리고 자세히 보면 클래스에 바로 원하는 값이 있는 게 아니라
클래스 안의 <a> 태그에 원하는 값이 있기 때문에 루프를 돌리면서 이 값도 find하고 text로 바꿔준다.
box = soup.find("tbody") all_singer = box.find_all("div", {"class":"ellipsis rank02"}) all_title = box.find_all("div", {"class":"ellipsis rank01"}) print(genre + "의 TOP 50곡") for singer, title in zip(all_singer, all_title): count += 1 print(str(count) + "위. " + title.find("a").text + " - " + singer.find("a").text)
4. 실행 결과
현재 댄스 장르 인기곡 순위
그리고 크롤링한 결과
5. 전체 코드
import requests from bs4 import BeautifulSoup while(True): genre = input("음악 장르 입력(발라드, 댄스, 힙합, 알앤비, 인디, 록, 트로트, 포크) : ") count = 0 if genre == "발라드": gnrCode = "GN0100" break elif genre == "댄스": gnrCode = "GN0200" break elif genre == "힙합": gnrCode = "GN0300" break elif genre == "알앤비": gnrCode = "GN0400" break elif genre == "인디": gnrCode = "GN0500" break elif genre == "록": gnrCode = "GN0600" break elif genre == "트로트": gnrCode = "GN0700" break elif genre == "포크": gnrCode = "GN0800" break else: print("장르 입력이 잘못 되었습니다. 다시 입력해주십시오.") header = {'User-Agent': 'Mozilla/5.0 (Windows NT 6.3; Trident/7.0; rv:11.0) like Gecko'} melon_url = "https://www.melon.com/genre/song_list.htm?gnrCode=" + gnrCode raw = requests.get(melon_url, headers = header) soup = BeautifulSoup(raw.text, "html.parser") box = soup.find("tbody") all_singer = box.find_all("div", {"class":"ellipsis rank02"}) all_title = box.find_all("div", {"class":"ellipsis rank01"}) print(genre + "의 TOP 50곡") for singer, title in zip(all_singer, all_title): count += 1 print(str(count) + "위. " + title.find("a").text + " - " + singer.find("a").text)