1

newby 웹 스크레이퍼 여기. 왜 내가 필요한 정보를 추출 할 수 없는지 궁금합니다. 코드는 다음과 같습니다 :BeautifulSoup 문제로 데이터 스크랩하기

from bs4 import BeautifulSoup 
import requests 

url = "http://www.mortgagenewsdaily.com/mortgage_rates/" 

r = requests.get(url) 

soup = BeautifulSoup(r.content) 

table = soup.find("table", {"class": "rangetable mtg-rates"}) 

for trs in table.find_all("tr", {"class": "rate-row"}): 
    for tds in trs.find_all("td"): 
     try: 
      product = tds[0].get_text() 
      today = tds[1].get_text() 
      yesterday = tds[2].get_text() 
      change = tds[3].get_text() 
      low = tds[4].get_text() 
      high = tds[5].get_text() 
     except: 
      print "-" 
      continue 

tds 내의 클래스에주의해야합니까? 그리고이 정보를 긁을 수있는 더 좋고/더 쉬운 방법이 있습니까?

도움 주셔서 감사합니다.

답변

1

tds에 대해 여분의 루프가있는 것이 가장 큰 문제입니다. 각 셀에 대한 변수를 갖는 대신 적절한 tr 요소

  • 에 도착

    • 사용 CSS Selectors 예를 들어, 데이터 구조를 사용

      또한, 코드에 다음의 개선을 적용 할 수있다 , namedtuple

    개선 작업 코드 :

    from collections import namedtuple 
    from bs4 import BeautifulSoup 
    import requests 
    
    url = "http://www.mortgagenewsdaily.com/mortgage_rates/" 
    r = requests.get(url) 
    
    soup = BeautifulSoup(r.content) 
    
    Item = namedtuple('Item', "product,today,yesterday,change,low,high") 
    for tr in soup.select("table.mtg-rates tr.rate-row"): 
        item = Item(*(td.get_text(strip=True) for td in tr.find_all("td"))) 
        print item 
    
    dict의 경우

    Item(product=u'30 Yr FRM', today=u'3.62%', yesterday=u'3.64%', change=u'-0.023.62%', low=u'3.60%', high=u'4.56%') 
    Item(product=u'15 Yr FRM', today=u'3.00%', yesterday=u'3.02%', change=u'-0.023.00%', low=u'2.98%', high=u'3.55%') 
    Item(product=u'FHA 30 Year Fixed', today=u'3.25%', yesterday=u'3.25%', change=u'--3.25%', low=u'3.25%', high=u'4.25%') 
    Item(product=u'Jumbo 30 Year Fixed', today=u'3.61%', yesterday=u'3.63%', change=u'-0.023.61%', low=u'3.58%', high=u'4.38%') 
    Item(product=u'5/1 Yr ARM', today=u'3.23%', yesterday=u'3.22%', change=u'+0.013.23%', low=u'3.17%', high=u'3.26%') 
    

    또는 :

    인쇄

    headers = ['product', 'today', 'yesterday' ,' change', 'low', 'high'] 
    for tr in soup.select("table.mtg-rates tr.rate-row"): 
        item = dict(zip(headers, [td.get_text(strip=True) for td in tr.find_all("td")])) 
        print item 
    

    인쇄 :

    {'product': u'30 Yr FRM', 'yesterday': u'3.64%', 'high': u'4.56%', 'low': u'3.60%', 'today': u'3.62%', ' change': u'-0.023.62%'} 
    {'product': u'15 Yr FRM', 'yesterday': u'3.02%', 'high': u'3.55%', 'low': u'2.98%', 'today': u'3.00%', ' change': u'-0.023.00%'} 
    {'product': u'FHA 30 Year Fixed', 'yesterday': u'3.25%', 'high': u'4.25%', 'low': u'3.25%', 'today': u'3.25%', ' change': u'--3.25%'} 
    {'product': u'Jumbo 30 Year Fixed', 'yesterday': u'3.63%', 'high': u'4.38%', 'low': u'3.58%', 'today': u'3.61%', ' change': u'-0.023.61%'} 
    {'product': u'5/1 Yr ARM', 'yesterday': u'3.22%', 'high': u'3.26%', 'low': u'3.17%', 'today': u'3.23%', ' change': u'+0.013.23%'} 
    
  • +0

    네, 그냥 오류를 발견했습니다. 당신의 도움을 주셔서 감사합니다. – herkyonparade