【问题标题】:Extract data table from a specific page with multiple same name tables using Python BeautifulSoup使用 Python BeautifulSoup 从具有多个同名表的特定页面中提取数据表
【发布时间】:2020-05-12 19:46:19
【问题描述】:

我对 python 和 BeautifulSoup 很陌生。我编写了以下代码来调用网站:https://www.baseball-reference.com/leagues/MLB-standings.shtml,目的是抓取底部名为“MLB 详细排名”的表格并导出为 CSV 文件。我的代码成功创建了一个 CSV 文件,但提取了错误的数据表,并且缺少包含团队名称的第一列。我的代码将“东区”表格拉到顶部(不包括第一列),而不是我的目标表格,底部有完整的“MLB 详细排名”表格。

想知道是否有一种简单的方法可以将 MLB 详细排名表拉到底部。当我检查页面时,我试图提取的特定表的 ID 是:“expanded_standings_overall”。我需要在我的代码中引用它吗?或者,将不胜感激任何其他重新编写代码以提取正确表的指导。再说一次,我很新,正在努力学习。

import requests
import csv
import datetime
from bs4 import BeautifulSoup

# static urls
season = datetime.datetime.now().year
URL = "https://www.baseball-reference.com/leagues/MLB-standings.shtml".format(season=season)

# request the data
batting_html = requests.get(URL).text

def parse_array_from_fangraphs_html(input_html, out_file_name):
    """
    Take a HTML stats page from fangraphs and parse it out to a CSV file.
    """
    # parse input
    soup = BeautifulSoup(input_html, "lxml")
    table = soup.find("table", class_=["sortable,", "stats_table", "now_sortable"])

    # get headers
    headers_html = table.find("thead").find_all("th")
    headers = []
    for header in headers_html:
        headers.append(header.text)
    print(headers)

    # get rows
    rows = []
    rows_html = table.find_all("tr")
    for row in rows_html:
        row_data = []
        for cell in row.find_all("td"):
            row_data.append(cell.text)
        rows.append(row_data)

    # write to CSV file
    with open(out_file_name, "w") as out_file:
        writer = csv.writer(out_file)
        writer.writerow(headers)
        writer.writerows(rows)

parse_array_from_fangraphs_html(batting_html, 'BBRefTest.csv')

【问题讨论】:

  • 请求的答案只包含 6 个表。看来您需要使用标题和/或会话才能获得完整答案。
  • 仅供参考,有一个相当流行的 Python 库可以用来抓取balloon-reference.com github.com/jldbc/pybaseball

标签: python python-3.x beautifulsoup


【解决方案1】:

首先,是的,最好引用 ID,因为您会怀疑开发人员已将此 ID 设置为该表的唯一 ID,而类只是样式描述符。

现在,问题更深了。快速浏览页面代码实际上表明定义表格的 html 被注释掉了上面的几个标签。我怀疑脚本在客户端(在您的浏览器中)“启用”了此代码。 requests.get 只是拉出 html 而不处理任何 javascript 不会捕获它(您可以检查 batting_html 的内容来验证)。

一个非常快速和肮脏的解决方法是捕获注释掉的代码并在 BeautifulSoup 中重新处理它:

from bs4 import Comment
...

# parse input
soup = BeautifulSoup(input_html, "lxml")
dynamic_content = soup.find("div", id="all_expanded_standings_overall")
comments = dynamic_content.find(string=lambda text: isinstance(text, Comment))
table = BeautifulSoup(comments, "lxml")

# get headers

顺便说一句,你想在写文件的时候指定utf8编码...

with open(out_file_name, "w", encoding="utf8") as out_file:
    writer = csv.writer(out_file)
    ...

现在这真的“又快又脏”,我会尝试更深入地检查 html 代码和 javascript,然后再将其扩展到其他页面。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-10-24
    • 1970-01-01
    • 2012-02-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多