在本文中,我们将介绍如何使用 Python 构建一个简单的试卷下载器。该应用程序可以从指定的网站下载试卷,并通过一个图形用户界面(GUI)来进行交互。我们将使用 requests
库进行网络请求,使用 BeautifulSoup
解析 HTML,使用 tkinter
创建 GUI。
注意:本文所示代码仅供学习和交流使用,严禁用于任何商业活动。请文明使用,尊重版权。
环境准备
在开始之前,请确保已经安装了以下库:
pip install requests
pip install beautifulsoup4
完整代码
以下是完整的代码实现:
#!/usr/bin/env python3
# coding:utf-8
import os
import requests
from bs4 import BeautifulSoup
import tkinter as tk
from tkinter import ttk, filedialog, messageboxdef fetch_page_count(url):response = requests.get(url)response.encoding = "gb2312"soup = BeautifulSoup(response.text, "html.parser")page = soup.find("ul", class_="pagelist")count = int(page.find("strong").string)base_url = page.find("a").get("href").rsplit("_", 1)[0]return count, base_urldef download_test_papers(page_url, version, save_path, base_url, progress, total_papers):response = requests.get(page_url)response.encoding = "gb2312"soup = BeautifulSoup(response.text, "html.parser")test_list = soup.find("ul", class_="c1")test_trs = test_list.find_all("tr")downloaded = 0for tr in test_trs:if version in tr.text:test_td = tr.find("a").get("href")name = tr.find("a").stringtest_url = base_url + test_tdtest_page = requests.get(test_url)test_page_soup = BeautifulSoup(test_page.text, "html.parser")downurl = test_page_soup.find("ul", class_="downurllist").find("a").get("href")download_file(base_url + downurl, os.path.join(save_path, name + ".rar"))downloaded += 1progress.set(downloaded)root.update_idletasks()if downloaded >= total_papers:returndef download_file(url, path):response = requests.get(url)with open(path, "wb") as file:file.write(response.content)def start_download():subject = subject_var.get()grade = grade_var.get()version = version_var.get()save_path = path_entry.get()total_papers = int(papers_var.get())if not subject or not grade or not version or not save_path or not total_papers:messagebox.showerror("错误", "所有字段都必须填写!")returnurl = base_url + subjects[subject] + grades[grade]try:page_count, page_base_url = fetch_page_count(url)except Exception as e:messagebox.showerror("错误", f"获取页面数据失败: {e}")returnif not os.path.exists(save_path):os.makedirs(save_path)try:progress.set(0)total_progress['maximum'] = total_papersfor page in range(1, page_count + 1):page_url = f"{url}/{page_base_url}_{page}.html"download_test_papers(page_url, version, save_path, base_url, progress, total_papers)if progress.get() >= total_papers:breakmessagebox.showinfo("完成", "所有试卷下载完成!")except Exception as e:messagebox.showerror("错误", f"下载过程中出错: {e}")def browse_path():path = filedialog.askdirectory()if path:path_entry.delete(0, tk.END)path_entry.insert(0, path)if __name__ == '__main__':base_url = "https://www.shijuan1.com"subjects = {"语文": "/a/sjyw", "数学": "/a/sjsx", "英语": "/a/sjyy", "物理": "/a/sjwl","化学": "/a/sjhx", "政治": "/a/sjzz", "历史": "/a/sjls", "地理": "/a/sjdl", "生物": "/a/sjsw"}grades = {"一年级": "1", "二年级": "2", "三年级": "3", "四年级": "4", "五年级": "5", "六年级": "6","七年级": "7", "八年级": "8", "九年级": "9", "中考": "zk", "高一": "g1", "高二": "g2", "高三": "g3","高考": "gk"}versions = ["人教版", "苏教版", "北师大版", "沪教版", "鲁教版", "其他"]# 创建主窗口root = tk.Tk()root.title("试卷下载器")# 科目选择tk.Label(root, text="科目:").grid(row=0, column=0, padx=10, pady=10)subject_var = tk.StringVar()subject_combobox = ttk.Combobox(root, textvariable=subject_var, values=list(subjects.keys()))subject_combobox.grid(row=0, column=1, padx=10, pady=10)# 年级选择tk.Label(root, text="年级:").grid(row=1, column=0, padx=10, pady=10)grade_var = tk.StringVar()grade_combobox = ttk.Combobox(root, textvariable=grade_var, values=list(grades.keys()))grade_combobox.grid(row=1, column=1, padx=10, pady=10)# 版本信息选择tk.Label(root, text="版本信息:").grid(row=2, column=0, padx=10, pady=10)version_var = tk.StringVar()version_combobox = ttk.Combobox(root, textvariable=version_var, values=versions)version_combobox.grid(row=2, column=1, padx=10, pady=10)# 保存路径选择tk.Label(root, text="保存路径:").grid(row=3, column=0, padx=10, pady=10)path_entry = tk.Entry(root)path_entry.grid(row=3, column=1, padx=10, pady=10)tk.Button(root, text="浏览...", command=browse_path).grid(row=3, column=2, padx=10, pady=10)# 下载份数选择tk.Label(root, text="下载份数:").grid(row=4, column=0, padx=10, pady=10)papers_var = tk.StringVar(value="10")papers_entry = tk.Entry(root, textvariable=papers_var)papers_entry.grid(row=4, column=1, padx=10, pady=10)# 进度条progress = tk.IntVar()total_progress = ttk.Progressbar(root, variable=progress, maximum=100)total_progress.grid(row=5, column=0, columnspan=3, padx=10, pady=10, sticky="ew")# 开始下载按钮tk.Button(root, text="开始下载", command=start_download).grid(row=6, column=0, columnspan=3, padx=10, pady=20)# 运行主循环root.mainloop()
代码解析
-
库导入和网络请求:
- 使用
requests
库进行网络请求。 - 使用
BeautifulSoup
解析 HTML。 - 使用
tkinter
创建 GUI。
- 使用
-
函数定义:
fetch_page_count(url)
:获取页面数量和基础 URL。download_test_papers(page_url, version, save_path, base_url, progress, total_papers)
:下载试卷。download_file(url, path)
:下载文件并保存到指定路径。start_download()
:开始下载的主逻辑。browse_path()
:浏览文件夹路径。
-
主程序:
- 创建 GUI,并设置各类控件:下拉框、文本框、按钮等。
- 使用
tkinter
的mainloop
运行主循环。
使用说明
- 选择科目:从下拉框中选择需要下载试卷的科目。
- 选择年级:从下拉框中选择年级。
- 选择版本:从下拉框中选择试卷版本。
- 选择保存路径:点击“浏览”按钮,选择下载文件保存路径。
- 输入下载份数:在文本框中输入需要下载的试卷份数。
- 开始下载:点击“开始下载”按钮,程序将自动开始下载试卷。
注意事项
- 网络连接:确保网络连接正常,避免下载过程中断。
- 下载路径:确保选择的下载路径有足够的存储空间。
- 文明使用:本程序仅供学习交流使用,严禁用于任何商业活动。
希望本文能对你有所帮助,带你一步步实现一个简单的试卷下载器。欢迎在评论区分享你的使用心得或提出问题!