【问题标题】:Web scraping using beautiful soup (sports data)使用美汤进行网页抓取(体育数据)
【发布时间】:2019-04-16 11:06:21
【问题描述】:

当我尝试加载此代码时,我收到两个错误。 1:第一个是我无法正确抓取name_text的数据。

2:我收到 team = name_text.div.text 的缩进错误。我知道这可能很容易解决,但我尝试了不同的缩进,但似乎没有任何效果。

我想在网站上获取球队名称和赔率。

<div class="size14_f7opyze Endeavour_fhudrb0 medium_f1wf24vo participantText_fivg86r" data-automation-id="participant-one">Orlando Magic</div>
<div class="priceText_f71sibe"><span class="size14_f7opyze medium_f1wf24vo priceTextSize_frw9zm9" data-automation-id="price-text">5.85</span></div>

上面的html是从网站上复制过来的。

from bs4 import BeautifulSoup
from urllib.request import urlopen as uReq
my_url = 'https://www.sportsbet.com.au/betting/basketball-us'
uClient = uReq(my_url)
page_html = uClient.read()
uClient.close()

soup = BeautifulSoup(page_html, "html.parser")

price_text = soup.findAll("div",{"class":"priceText_f71sibe"})
name_text = soup.findAll("div",{"class":"size14_f7opyze Endeavour_fhudrb0 medium_f1wf24vo participantText_fivg86r"})
filename = "odds.csv"
f = open(filename,"w")
headers = "Team, odds_team\n"
print(name_text)
f.write(headers)

for price_text in price_texts:
team = name_text.div.text
odds = price_text.span.text

print(odds)
print(team + odds)
f.write(team + "," + odds + "\n")
f.close()

任何帮助都会很棒。干杯。

【问题讨论】:

    标签: python web-scraping beautifulsoup


    【解决方案1】:

    您的for loop 缩进不正确。正确的缩进是:

    for price_text in price_texts:
        team = name_text.div.text
        odds = price_text.span.text
        team = name_text.div.text
        odds = price_text.span.text
    
        print(odds)
        print(team + odds)
        f.write(team + "," + odds + "\n")
    f.close()
    

    队前有 4 个空格和赔率。请阅读Python ForLoop documentation

    另外,没有price_texts 变量。您需要在执行 findAll 时分配它,您忘记了一个“S”:

    price_texts = soup.findAll("div",{"class":"priceText_f71sibe"})
    

    最后,考虑使用with 而不是open().close() 写入文件。

    【讨论】:

    • 感谢 cmets。循环现在更有意义了。您是否有重复 team = name_text.div.text 和 odds = price_text.span.text 的原因?当我到达线路 team = name_text.div.text 时出现错误。该错误指出未定义名称“name_text”,但我不明白为什么,因为我对赔率进行了类似的处理,并且它对赔率有效。
    【解决方案2】:

    我在想你可以做的只是迭代并将它们存储到列表中,然后写入文件。不幸的是,我无法在工作中访问该站点,因此无法测试代码,但我相信这应该会提供您正在寻找的输出:

    from bs4 import BeautifulSoup
    from urllib.request import urlopen as uReq
    import csv
    from itertools import zip_longest
    
    my_url = 'https://www.sportsbet.com.au/betting/basketball-us'
    uClient = uReq(my_url)
    page_html = uClient.read()
    uClient.close()
    
    soup = BeautifulSoup(page_html, "html.parser")
    
    price_text = soup.findAll("span",{"data-automation-id":"price-text"})
    name_text = soup.findAll("div",{"data-automation-id":"participant-one"})
    
    team_list = [ name.text.strip() for name in name_text ]
    odds_list = [ price.text.strip() for price in price_text ]
    
    d = [team_list, odds_list]
    export_data = zip_longest(*d, fillvalue = '')
    with open('odds.csv', 'w', encoding="ISO-8859-1", newline='') as myfile:
          wr = csv.writer(myfile)
          wr.writerow(("Team", "odds_team"))
          wr.writerows(export_data)
    myfile.close()
    

    【讨论】:

    • 这超出了我的能力范围,但确实没有错误。但是,它不会生成团队名称列表。标题 1 下方没有名称,但标题 2 下方确实有赔率。
    • 好的。我会在上班时调整它。就像我说的那样,可以访问该站点。确保团队的 findAll 正确获取团队名称。另一种可能性是有空白。所以我现在将对其进行编辑,但就像我说的那样,稍后会进行更深入的了解。
    • 查看 OP,我可能会选择使用 data-automation-id,而不是 class。就像我说的,我会稍微修正一下代码,并解释每一点,以便您了解它在做什么。
    • @mclo 我对代码进行了编辑。试试看你会得到什么
    【解决方案3】:

    你可以试试这个吗?

    from bs4 import BeautifulSoup
    from urllib.request import urlopen as uReq
    my_url = 'https://www.sportsbet.com.au/betting/basketball-us'
    uClient = uReq(my_url)
    page_html = uClient.read()
    uClient.close()
    
    soup = BeautifulSoup(page_html, "html.parser")
    
    price_texts = soup.findAll("div",{"class":"priceText_f71sibe"})
    name_texts = soup.findAll("div",{"class":"size14_f7opyze Endeavour_fhudrb0 medium_f1wf24voparticipantText_fivg86r"})
    filename = "odds.csv"
    f = open(filename,"w")
    headers = "Team, odds_team\n"
    print(name_text)
    f.write(headers)
    
    odds =''
    team=''
    for price_text in price_texts:
        odds = price_text.text
    for name_text in name_texts:
        team = name_text.text
    print(odds)
    print(team + odds)
    f.write(team + "," + odds + "\n")
    f.close()
    

    【讨论】:

    • 这几乎可以工作。它得到一个错误 NameError: name 'team' is not defined。与上面的响应相同的错误。我很难过。这个项目对于学习基本 python 的人来说太高级了。
    • 我的错。您必须在 for 循环之前定义团队和赔率。我已经编辑过了
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-03-30
    • 2021-12-06
    • 2019-05-05
    • 1970-01-01
    • 2022-01-08
    • 2022-01-20
    • 1970-01-01
    相关资源
    最近更新 更多