You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python Selenium爬取MLB球员数据:动态分页遍历方案求助

MLB官网球员数据爬取:动态分页遍历方案

问题背景

需要从MLB官网爬取球员数据,现有代码通过固定XPath列表手动指定第2-7页进行遍历,但实际分页数量不固定,无法适配所有情况。此前尝试定位分页父容器统计子div数量未达预期,需要实现能自动识别所有页码并遍历点击的动态分页方案。

原固定页数实现代码

import time
from selenium import webdriver
from selenium.webdriver.common.by import By

url = r"https://www.mlb.com/stats/"
driver = webdriver.Firefox()
time.sleep(5)
driver.get(url)
time.sleep(5)

# 下载第1页数据
# ...

# 第2-7页的XPath列表
pages = [
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[1]/div[2]/button/span",
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[1]/div[3]/button/span",
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[2]/div[4]/button",
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[2]/div[5]/button",
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[2]/div[6]/button/span",
    "/html/body/main/div[4]/section/section/div[3]/div[2]/div/div/div[2]/div[7]/button/span"
]

# 遍历第2-7页
k = 0
for page in pages:
    k = k + 1
    print("Page "+str(k+1))
    print("Loop "+str(k), page)
    # 滚动到页面底部使分页可见
    if k == 1:
        driver.maximize_window() # 最大化窗口
        driver.execute_script("window.scrollTo(0,document.body.scrollHeight)")
        time.sleep(5)
    pageButtonSelect = driver.find_element(By.XPATH, page)
    pageButtonSelect.click()
    time.sleep(5)
    # 下载当前页25名球员数据
    # ...

改进后的动态分页实现代码

import time
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

url = r"https://www.mlb.com/stats/"
driver = webdriver.Firefox()
driver.get(url)
# 用显式等待代替固定sleep,确保页面核心元素加载完成
WebDriverWait(driver, 10).until(
    EC.presence_of_element_located((By.CLASS_NAME, "stats-table"))
)

# 下载第1页数据
print("处理第1页数据")
# ... 此处添加你的数据下载逻辑

# 滚动到分页控件区域,确保元素可见
driver.execute_script("window.scrollTo(0, document.body.scrollHeight)")
time.sleep(2)

# 定位分页容器,获取所有页码按钮(排除上一页/下一页箭头,只取数字按钮)
# 通过按钮的aria-label属性筛选页码按钮,更可靠
pagination_container = WebDriverWait(driver, 10).until(
    EC.presence_of_element_located((By.XPATH, '//div[contains(@class, "pagination")]'))
)
# 获取所有带有"Go to page" aria-label的按钮,这些是数字页码按钮
page_buttons = pagination_container.find_elements(By.XPATH, './/button[contains(@aria-label, "Go to page")]')

# 遍历第2页及以后的页码按钮
for idx, button in enumerate(page_buttons[1:], start=2):
    print(f"处理第{idx}页数据")
    # 重新定位按钮(避免页面刷新后元素失效)
    current_button = WebDriverWait(driver, 10).until(
        EC.element_to_be_clickable((By.XPATH, f'.//button[contains(@aria-label, "Go to page {idx}")]'))
    )
    current_button.click()
    # 等待页面数据刷新
    WebDriverWait(driver, 10).until(
        EC.staleness_of(driver.find_element(By.CLASS_NAME, "stats-table"))
    )
    WebDriverWait(driver, 10).until(
        EC.presence_of_element_located((By.CLASS_NAME, "stats-table"))
    )
    # 下载当前页数据
    # ... 此处添加你的数据下载逻辑

driver.quit()

关键改进说明

  • 避免绝对XPath:改用相对定位和属性筛选(如aria-label),降低页面结构变化导致的定位失败概率。
  • 显式等待替代固定sleep:通过WebDriverWait等待元素加载/可点击/页面刷新,提升代码稳定性。
  • 动态识别页码:直接从分页容器中提取所有数字页码按钮,自动适配任意页数。
  • 元素重定位:每次点击页码后重新定位按钮,避免页面刷新后元素引用失效。

内容的提问来源于stack exchange,提问作者Dan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 08:17:41