Open kevin111234 opened 3 months ago
물론입니다. 함수 부분의 코드 한 줄 한 줄을 자세히 분석해보겠습니다. 두 개의 주요 함수인 news_collector
와 each_day_news
를 순서대로 설명하겠습니다.
news_collector
함수이 함수는 특정 검색어에 대해 네이버 뉴스에서 기사를 수집하고, 기사 본문을 텍스트로 추출합니다.
def news_collector(search, media, make_date1, make_date2):
url = f'https://search.naver.com/search.naver?where=news&query={search}&sm=tab_opt&sort=0&photo=0&field=0&pd=3&ds={make_date1}&de={make_date2}&docid=&related=0&mynews=1&office_type=1&office_section_code=1&news_office_checked={media}&nso=so%3Ar%2Cp%3Afrom{make_date1.replace(".","")}%2Cto{make_date2.replace(".","")}&start=1'
url
: 네이버 뉴스 검색 페이지에 접근하기 위한 URL을 동적으로 생성합니다.
search
: 사용자가 입력한 주식 종목명입니다.media
: 특정 언론사를 필터링하기 위한 매체 코드입니다.make_date1
, make_date2
: 검색할 날짜 범위입니다. start=1
은 첫 페이지부터 검색을 시작하도록 설정합니다. req = requests.get(url, headers=headers)
soup = bs(req.text, 'html.parser')
requests.get(url, headers=headers)
: requests
라이브러리를 사용하여 URL에 GET 요청을 보냅니다. headers
는 웹 요청 시 사용자가 설정한 User-Agent를 포함합니다.soup = bs(req.text, 'html.parser')
: BeautifulSoup
을 사용하여 HTML 문서를 파싱합니다. req.text
는 HTML 페이지의 내용을 가져오며, 'html.parser'
는 파싱에 사용되는 파서입니다. naver_news = soup.find_all('a', class_='news_tit')
soup.find_all('a', class_='news_tit')
: BeautifulSoup
을 사용해 class
가 'news_tit'
인 모든 <a>
태그를 찾아 리스트로 반환합니다. 이는 뉴스 기사 제목 링크들을 의미합니다. news_list = []
for news in naver_news:
url = news['href']
req = requests.get(url, headers=headers)
soup = bs(req.text, 'html.parser')
news_list = []
: 수집한 뉴스 본문을 저장할 빈 리스트를 초기화합니다.for news in naver_news:
: 찾은 모든 뉴스 제목 링크에 대해 반복문을 실행합니다.url = news['href']
: 뉴스 기사 링크의 URL을 가져옵니다.req = requests.get(url, headers=headers)
: 뉴스 기사 페이지에 대해 GET 요청을 보냅니다.soup = bs(req.text, 'html.parser')
: 다시 HTML 문서를 파싱하여 기사 본문을 추출할 준비를 합니다. try:
article_body = soup.find('div', class_='go_trans _article_content').get_text()
article_body = re.sub(r'\([^)]*\)', '', article_body)
article_body = re.sub(r'\[[^]]*\]', '', article_body)
article_body = re.sub(r'\<[^)]*\>', '', article_body)
article_body = article_body.replace('\n', ' ').replace('\t', ' ').strip()
news_list.append(article_body)
except:
pass
try:
: 뉴스 기사 본문을 추출하는 과정에서 발생할 수 있는 오류를 처리하기 위해 try-except
구문을 사용합니다.article_body = soup.find('div', class_='go_trans _article_content').get_text()
: 기사 본문이 포함된 <div>
태그를 찾아 텍스트를 추출합니다.()
), 대괄호([]
), HTML 태그(< >
) 등을 제거합니다.
re.sub(r'\([^)]*\)', '', article_body)
: 괄호 안의 내용을 제거합니다.re.sub(r'\[[^]]*\]', '', article_body)
: 대괄호 안의 내용을 제거합니다.re.sub(r'\<[^)]*\>', '', article_body)
: HTML 태그를 제거합니다.article_body.replace('\n', ' ').replace('\t', ' ').strip()
: 텍스트 내의 줄 바꿈(\n
)과 탭(\t
)을 공백으로 바꾸고, 양쪽 끝의 공백을 제거합니다.news_list.append(article_body)
: 정리된 텍스트를 news_list
에 추가합니다.except:
: 만약 기사 본문 추출에 실패하면 예외를 처리하고, 해당 뉴스는 무시됩니다. return news_list
return news_list
: 수집된 뉴스 기사 본문을 리스트 형태로 반환합니다.each_day_news
함수이 함수는 주어진 날짜에 대해 news_collector
함수를 호출하여 뉴스 데이터를 수집하고, 그 데이터를 keyword
데이터프레임에 추가합니다.
def each_day_news(date):
date = date.strftime('%Y.%m.%d')
make_date = date.replace('.', '')
make_date1 = date
make_date2 = date
date.strftime('%Y.%m.%d')
: datetime
형식의 날짜를 'YYYY.MM.DD' 형식의 문자열로 변환합니다.make_date = date.replace('.', '')
: 날짜에서 '.'을 제거하여 make_date
에 저장합니다.make_date1
, make_date2
: 검색할 날짜 범위를 설정합니다. 여기서는 동일한 날짜로 설정하여 해당 날짜의 뉴스만 검색합니다. mk = news_collector(stock_name, '1009', make_date1, make_date2) # 매일경제
ed = news_collector(stock_name, '1018', make_date1, make_date2) # 이데일리
yh = news_collector(stock_name, '1020', make_date1, make_date2) # 연합뉴스
fn = news_collector(stock_name, '1015', make_date1, make_date2) # 파이낸셜뉴스
ks = news_collector(stock_name, '1008', make_date1, make_date2) # 한국경제
news = mk + ed + yh + fn + ks
news_collector
함수를 사용하여 특정 언론사(매일경제, 이데일리, 연합뉴스, 파이낸셜뉴스, 한국경제)의 뉴스 기사를 수집합니다. 각 언론사의 고유 코드(예: '1009'는 매일경제)가 사용됩니다.news = mk + ed + yh + fn + ks
: 수집된 모든 뉴스 기사를 하나의 리스트로 합칩니다. news_noun = []
for i in news:
noun = hannanum.nouns(i)
news_noun += noun
count = Counter(news_noun)
top_10 = count.most_common(10)
news_noun = []
: 뉴스 기사에서 추출한 명사들을 저장할 리스트를 초기화합니다.for i in news:
: 수집된 뉴스 기사 리스트에서 각 기사를 순회합니다.noun = hannanum.nouns(i)
: Hannanum
분석기를 사용해 각 기사에서 명사를 추출합니다.news_noun += noun
: 추출된 명사를 news_noun
리스트에 추가합니다.count = Counter(news_noun)
: Counter
를 사용해 명사의 출현 빈도를 계산합니다.top_10 = count.most_common(10)
: 출현 빈도가 높은 상위 10개의 명사를 추출합니다. keyword.loc[keyword['Date'] == date, 'Top1':'Top10'] = [i[0] for i in top_10]
keyword.loc[keyword['Date'] == date, 'Top1':'Top10'] = [i[0] for i in top_10]
: 추출된 상위 10개의 명사를 keyword
데이터프레임의 해당 날짜에 저장합니다. 예를 들어, 'Top1'은 가장 많이 등장한 명사를, 'Top2'는 두 번째로 많이 등장한 명사를 저장합니다.
main_news = news_collector(stock_name, '1001', make_date1, make_date2) # 네이버 금융 메인 뉴스
main_news_noun = []
for i in main_news:
물론입니다! 코드를 자세하게 분석해 보겠습니다. 코드는 주식 데이터를 기반으로 관련 뉴스를 수집하고, 이 뉴스에서 핵심 키워드를 추출하여 주가 변동과 함께 시각화하는 작업을 수행합니다. 이 코드의 구성 요소와 작동 방식을 라이브러리 및 함수 설명을 포함해 단계별로 설명하겠습니다.
1. 필요한 라이브러리 임포트
pandas
: 데이터 처리를 위한 라이브러리로, 특히 데이터프레임 형태로 데이터를 관리하는 데 사용됩니다.requests
: HTTP 요청을 보내 웹 페이지의 데이터를 가져오는 데 사용됩니다.re
: 정규 표현식을 사용해 텍스트에서 특정 패턴을 검색하거나 수정하는 데 사용됩니다.BeautifulSoup (bs4)
: HTML 및 XML 문서를 파싱하여 필요한 데이터를 추출하는 데 사용됩니다.fake_useragent
: 웹 스크래핑할 때 사용하는User-Agent
를 무작위로 생성하여 사용합니다. 이렇게 하면 요청이 차단될 가능성을 줄일 수 있습니다.plotly.express
: 데이터 시각화를 위한 라이브러리로, 인터랙티브한 그래프를 그리는 데 사용됩니다.collections.Counter
: 리스트나 문자열에서 요소의 빈도 수를 계산하는 데 사용됩니다.konlpy.tag.Hannanum
: 한국어 자연어 처리를 위한 라이브러리 중 하나로, 여기서는 명사 추출에 사용됩니다.FinanceDataReader (fdr)
: 주식 시장 데이터를 가져오는 데 사용됩니다.warnings
: 경고 메시지를 무시하도록 설정하는 데 사용됩니다.2. 초기 설정 및 데이터 수집
Hannanum
초기화: 한국어 텍스트에서 명사를 추출하기 위해Hannanum
형태소 분석기를 초기화합니다.fdr.StockListing('KRX')
: 한국거래소(KRX)에 상장된 모든 주식 종목의 목록을 데이터프레임 형태로 가져옵니다.UserAgent()
: 가짜User-Agent
값을 생성하여headers
에 저장합니다. 웹 요청 시 이 값을 사용하여 스크래핑 차단을 피하려고 합니다.3. 사용자 입력 및 주가 데이터 수집
df_krx
데이터프레임에서 입력한 종목명의 코드(주식 번호)를 찾아stock_num
에 저장합니다.FinanceDataReader
를 사용해 해당 종목의 주가 데이터를 가져옵니다. 여기서 'Date'와 'Close'(종가)만 선택하여 데이터프레임을 생성합니다.4. 데이터 프레임 초기화
Top1
부터Top10
까지의 주요 키워드와Main_News1
부터Main_News10
까지의 메인 뉴스 키워드가 포함됩니다.keyword
라는 데이터프레임을 생성하고, 주가 데이터에서 'Date'와 'Close'를 복사합니다.5. 뉴스 수집 및 키워드 분석 함수
5.1
news_collector
함수search
: 검색할 키워드(여기서는 주식 종목명).media
: 특정 매체의 코드 (예: 매일경제, 이데일리 등).make_date1
,make_date2
: 뉴스 검색 범위에 해당하는 시작 및 종료 날짜.news_list
에 저장합니다.5.2
each_day_news
함수keyword
데이터프레임에 저장합니다.date
: 분석할 날짜.Hannanum
형태소 분석기를 사용해 명사를 추출하고, 단어 빈도를 계산하여 상위 10개 키워드를 추출합니다.keyword
데이터프레임의 해당 날짜에 저장합니다.6. 뉴스 데이터 처리 및 시각화
keyword
데이터프레임의 각 날짜에 대해each_day_news
함수를 적용하여 뉴스 데이터를 수집하고 키워드를 추출합니다.keyword2
라는 새로운 데이터프레임을 생성하며, 결측값(NaN)은 공백으로 채웁니다.plotly.express
를 사용해 주가 데이터를 시각화합니다. 그래프에 마우스를 올리면 해당 날짜의 뉴스 키워드가 함께 표시되도록 설정합니다.정리
이 코드의 목적은 주식 종목의 과거 주가 데이터와 관련 뉴스 데이터를 수집하고, 이를 바탕으로 주가와 뉴스 키워드의 변동을 시각화하는 것입니다. 네이버 뉴스와 네이버 금융에서 데이터를 수집하며, 한국어 텍스트 처리를 통해 중요한 키워드를 추출합니다. 이렇게 수집된 데이터를 사용하여 주가 변동과 뉴스 키워드 간의 연관성을 시각적으로 분석할 수 있습니다.