news 2026/5/21 22:47:13

Python爬虫实战:requests + BeautifulSoup4采集经典标靶网站哲理名言,并导出结构化文件!

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Python爬虫实战:requests + BeautifulSoup4采集经典标靶网站哲理名言,并导出结构化文件!

㊗️本期内容已收录至专栏《Python爬虫实战》,持续完善知识体系与项目实战,建议先订阅收藏,后续查阅更方便~
㊙️本期爬虫难度指数:⭐ (入门级)
🉐福利:一次订阅后,专栏内的所有文章可永久免费看,持续更新中,保底1000+(篇)硬核实战内容。

全文目录:

      • 🌟 开篇语
      • 0️⃣ 前言(Preface)
      • 1️⃣ 摘要(Abstract)
      • 2️⃣ 背景与需求(Why)
      • 3️⃣ 合规与注意事项(必写)⚠️
      • 4️⃣ 技术选型与整体流程(What/How)
      • 5️⃣ 环境准备与依赖安装(可复现)💻
      • 6️⃣ 核心实现:请求层(Fetcher)
      • 7️⃣ 核心实现:解析层(Parser)
      • 8️⃣ 数据存储与导出(Storage)
      • 9️⃣ 运行方式与结果展示(必写)🚀
      • 🔟 常见问题与排错(强烈建议写)🔧
      • 1️⃣1️⃣ 进阶优化(可选但加分)🌟
      • 1️⃣2️⃣ 总结与延伸阅读
      • 🌟 文末
        • ✅ 专栏持续更新中|建议收藏 + 订阅
        • ✅ 互动征集
        • ✅ 免责声明

🌟 开篇语

哈喽,各位小伙伴们你们好呀~我是【喵手】。
运营社区: C站 / 掘金 / 腾讯云 / 阿里云 / 华为云 / 51CTO
欢迎大家常来逛逛,一起学习,一起进步~🌟

我长期专注Python 爬虫工程化实战,主理专栏 《Python爬虫实战》:从采集策略反爬对抗,从数据清洗分布式调度,持续输出可复用的方法论与可落地案例。内容主打一个“能跑、能用、能扩展”,让数据价值真正做到——抓得到、洗得净、用得上

📌专栏食用指南(建议收藏)

  • ✅ 入门基础:环境搭建 / 请求与解析 / 数据落库
  • ✅ 进阶提升:登录鉴权 / 动态渲染 / 反爬对抗
  • ✅ 工程实战:异步并发 / 分布式调度 / 监控与容错
  • ✅ 项目落地:数据治理 / 可视化分析 / 场景化应用

📣专栏推广时间:如果你想系统学爬虫,而不是碎片化东拼西凑,欢迎订阅专栏👉《Python爬虫实战》👈,一次订阅后,专栏内的所有文章可永久免费阅读,持续更新中。

💕订阅后更新会优先推送,按目录学习更高效💯~

0️⃣ 前言(Preface)

  • 项目核心:本篇我们将使用 Python 的requests+BeautifulSoup4工具,抓取经典标靶网站的哲理名言,最终产出一份结构化的英文命名数据集文件。

  • 读完本文你能获得什么

    1. 掌握静态网页爬虫的“黄金四步法”(请求、解析、清洗、存储)。
    2. 学会编写具备基础容错和重试机制的工业级网络请求代码。
    3. 获得一份可以直接运行并产出数据的实战源码,为后续进阶打下坚实基础。

1️⃣ 摘要(Abstract)

  • 项目核心:本文旨在通过轻量级库requestsbs4解析目标静态 HTML 页面,提取文本与属性,并将清洗后的数据持久化至本地 CSV 文件中。

  • 读完本文你能获得什么

    1. 理解合法合规采集数据的重要原则(如遵循robots.txt)。
    2. 精通基于 CSS 选择器的 DOM 树解析与异常字段捕获技巧。
    3. 了解爬虫开发中常见的 403/429 错误排查与进阶优化思路。

2️⃣ 背景与需求(Why)

为什么要爬?
说实话,很多人学爬虫一开始只是觉得“酷”,但在实际业务中,爬虫是数据分析的源泉信息聚合的核心驱动力。假设我们需要训练一个自然语言处理(NLP)的“每日一言”大模型,或者只是想给自己的博客做一个自动更新的“名言警句”侧边栏,手动复制粘贴显然不够极客。我们需要通过自动化手段,快速构建属于自己的知识图谱。

目标站点与字段:

  • 目标站点http://quotes.toscrape.com/(官方合法的爬虫测试沙盒)

  • 目标字段清单

    • Quote_Text(名言内容)
    • Author(作者姓名)
    • Tags(名言相关标签,由于可能有多个,我们将以逗号分隔)

3️⃣ 合规与注意事项(必写)⚠️

作为一名资深爱好者,我必须提醒你,技术无罪,但使用技术要有底线。

  1. 遵循 robots.txt:在爬取任何网站前,请习惯性地访问域名/robots.txt,查看站长允许或禁止抓取的目录。
  2. 频率控制(不要攻击式并发):不要像发起 DDoS 攻击一样去请求别人的服务器。加上time.sleep()延时,温柔一点,细水长流。
  3. 不采集敏感信息:坚决不碰涉及个人隐私、国家安全的数据。
  4. 不绕过付费/登录限制:尊重内容创作者的知识产权,我们只获取公开的互联网公共信息。

4️⃣ 技术选型与整体流程(What/How)

技术定调:静态网页爬取
目标网站服务端直接通过 HTML 返回了完整的数据内容,没有使用复杂的 Ajax 动态加载或加密混淆。因此,这属于最经典的静态网页爬虫

为什么选requests+bs4
俗话说“杀鸡焉用牛刀”,面对这种结构清晰的静态网站,上Scrapy框架有点重,用Playwright渲染引擎又太浪费系统资源。requests负责高效建立 HTTP 通信,BeautifulSoup的 CSS 选择器写起来直观且优雅,是本场景的最佳组合。

整体流程图如下(English visualization as requested):

5️⃣ 环境准备与依赖安装(可复现)💻

无论你是小白还是老鸟,拥有一个干净的虚拟环境都是好习惯。加油,把这几行命令敲起来!

  • Python 版本:推荐 Python 3.8 或以上版本。

  • 依赖安装

    pipinstallrequests beautifulsoup4 pandas
  • 推荐项目结构

    quote_spider/ ├── main.py # 入口启动文件 ├── fetcher.py # 网络请求模块 ├── parser.py # 页面解析模块 ├── storage.py # 数据存储模块 └── data/ # 存放输出文件的目录

    (为了方便你直接复制运行,接下来的代码我会整合在一个优雅的脚本中)

6️⃣ 核心实现:请求层(Fetcher)

这一层是爬虫的“敲门砖”。不带Headers的请求就像没穿衣服在街上跑,很容易被服务器封禁。

importrequestsimporttimeimportlogging logging.basicConfig(level=logging.INFO,format='%(asctime)s - %(levelname)s - %(message)s')deffetch_page(url,retries=3):# 必须说明:模拟真实浏览器的 Headersheaders={'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/115.0.0.0 Safari/537.36','Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8','Referer':'http://quotes.toscrape.com/'# 告诉服务器我从哪里来}forattemptinrange(retries):try:# 必须说明:加上 timeout 防止死锁挂起response=requests.get(url,headers=headers,timeout=10)response.raise_for_status()# 遇到 4xx 或 5xx 会抛出异常returnresponse.textexceptrequests.exceptions.RequestExceptionase:logging.warning(f"Fetch failed on{url}. Attempt{attempt+1}of{retries}. Error:{e}")time.sleep(2**attempt)# 指数退避策略:失败后等待 1s, 2s, 4slogging.error(f"Max retries reached for{url}")returnNone

7️⃣ 核心实现:解析层(Parser)

拿到 HTML 源码后,我们要精准地“摘取”数据。这里采用bs4的 CSS 选择器(.select())。

frombs4importBeautifulSoupdefparse_quotes(html_content):ifnothtml_content:return[],Nonesoup=BeautifulSoup(html_content,'html.parser')quotes_data=[]# 获取列表页中的所有名言块quote_blocks=soup.select('div.quote')forblockinquote_blocks:# 提取字段并做容错处理(缺失字段怎么办?用 .get_text() 前先判断)text_element=block.select_one('span.text')quote_text=text_element.get_text(strip=True)iftext_elementelse"Unknown Quote"author_element=block.select_one('small.author')author=author_element.get_text(strip=True)ifauthor_elementelse"Unknown Author"tags_elements=block.select('div.tags a.tag')tags=[tag.get_text(strip=True)fortagintags_elements]tags_str=", ".join(tags)iftagselse"No Tags"quotes_data.append({'Quote_Text':quote_text,'Author':author,'Tags':tags_str})# 获取下一页的链接next_btn=soup.select_one('li.next a')next_url=f"http://quotes.toscrape.com{next_btn['href']}"ifnext_btnelseNonereturnquotes_data,next_url

8️⃣ 数据存储与导出(Storage)

这里我们选择极其通用且易于数据分析的CSV格式。我们使用 URL 或内容的 Hash 来去重这里不需要,因为目标网站分页明确无重复,但为了严谨,我们基于Quote_Text做简单的去重校验。

importcsvimportosdefsave_to_csv(data_list,filename="quotes_dataset.csv"):ifnotdata_list:return# 去重策略:按名言内容去重seen=set()unique_data=[]foritemindata_list:ifitem['Quote_Text']notinseen:seen.add(item['Quote_Text'])unique_data.append(item)# 字段映射与存储keys=['Quote_Text','Author','Tags']file_exists=os.path.isfile(filename)withopen(filename,'a',newline='',encoding='utf-8')asoutput_file:dict_writer=csv.DictWriter(output_file,fieldnames=keys)ifnotfile_exists:dict_writer.writeheader()dict_writer.writerows(unique_data)logging.info(f"Successfully saved{len(unique_data)}unique records to{filename}.")

9️⃣ 运行方式与结果展示(必写)🚀

将上面的代码拼接在一起(你可以自行加一个main()函数,并在其中加上time.sleep(1)翻页逻辑)。

  • 启动命令:打开你的终端,运行:

    python main.py
  • 输出位置:代码将在当前目录生成一个名为quotes_dataset.csv的文件。

  • 示例结果(前3行)

Quote_TextAuthorTags
“The world as we have created it is a process of our thinking. It cannot be changed without changing our thinking.”Albert Einsteinchange, deep-thoughts, thinking, world
“It is our choices, Harry, that show what we truly are, far more than our abilities.”J.K. Rowlingabilities, choices
“There are only two ways to live your life. One is as though nothing is a miracle. The other is as though everything is a miracle.”Albert Einsteininspirational, life, live, miracle

🔟 常见问题与排错(强烈建议写)🔧

爬虫总会遇到各种玄学问题,别气馁,排错过程才是长知识的黄金时刻!

  • 遇上 403 或 429 怎么办?:403 通常是因为你的 Headers 太假了,尤其是缺失了真实的User-Agent或者Referer。429 说明你的访问频率触碰了站点的警报线。解法:加大time.sleep()延迟,或者建立代理 IP 池轮换 IP。
  • 抓下来的 HTML 全是 JS 脚本的空壳?:恭喜你,遇到了 SPA(单页应用,如 Vue/React 开发的网站)。静态请求拿不到数据了。解法:按 F12 打开开发者工具,看Network->XHR/Fetch,直接去抓取背后的 JSON 数据接口 API。
  • 解析报错(NoneType' object has no attribute 'get_text')?:这是因为网站结构变化或某个元素本来就不存在。解法:在.get_text()前一定要做非空判断(参考本文第7节的容错写法)。
  • 中文乱码怎么破?requests有时会猜错网页编码,直接在解析前强制声明:response.encoding = 'utf-8'

1️⃣1️⃣ 进阶优化(可选但加分)🌟

如果你已经玩透了基础的,想要挑战更强大的架构:

  1. 并发加速:把简单的for循环换成concurrent.futures.ThreadPoolExecutor,实现多线程抓取,速度起飞!但记住,线程池越大,越容易被封。
  2. 断点续跑:如果网站有 10000 页,爬到 5000 页断网了怎么办?可以引入 Redis 集合存储已经爬取过的 URL,每次开跑前做一次差集比对。
  3. 定时调度:结合服务器的crontab或者更高级的Apache Airflow,每天早上 8 点自动抓取更新数据。

1️⃣2️⃣ 总结与延伸阅读

🎉 恭喜你读到了这里!复盘一下,我们今天用 Python 完成了一套完整的爬虫闭环:从设置带重试机制的网络请求,到 CSS 结构化解析,最后稳稳地把干干净净的数据存入了CSV中。

下一步的打怪升级方向

当你遇到需要滑动验证码、需要执行 JavaScript 或者点击翻页的复杂网站时,这套基础方案就不够用了。接下来你可以去了解Playwright(无头浏览器自动化控制)以及工业级的Scrapy爬虫框架。

🌟 文末

好啦~以上就是本期的全部内容啦!如果你在实践过程中遇到任何疑问,欢迎在评论区留言交流,我看到都会尽量回复~咱们下期见!

小伙伴们在批阅的过程中,如果觉得文章不错,欢迎点赞、收藏、关注哦~
三连就是对我写作道路上最好的鼓励与支持!❤️🔥

✅ 专栏持续更新中|建议收藏 + 订阅

墙裂推荐订阅专栏 👉 《Python爬虫实战》,本专栏秉承着以“入门 → 进阶 → 工程化 → 项目落地”的路线持续更新,争取让每一期内容都做到:

✅ 讲得清楚(原理)|✅ 跑得起来(代码)|✅ 用得上(场景)|✅ 扛得住(工程化)

📣想系统提升的小伙伴:强烈建议先订阅专栏 《Python爬虫实战》,再按目录大纲顺序学习,效率十倍上升~

✅ 互动征集

想让我把【某站点/某反爬/某验证码/某分布式方案】等写成某期实战?

评论区留言告诉我你的需求,我会优先安排实现(更新)哒~


⭐️ 若喜欢我,就请关注我叭~(更新不迷路)
⭐️ 若对你有用,就请点赞支持一下叭~(给我一点点动力)
⭐️ 若有疑问,就请评论留言告诉我叭~(我会补坑 & 更新迭代)


✅ 免责声明

本文爬虫思路、相关技术和代码仅用于学习参考,对阅读本文后的进行爬虫行为的用户本作者不承担任何法律责任。

使用或者参考本项目即表示您已阅读并同意以下条款:

  • 合法使用: 不得将本项目用于任何违法、违规或侵犯他人权益的行为,包括但不限于网络攻击、诈骗、绕过身份验证、未经授权的数据抓取等。
  • 风险自负: 任何因使用本项目而产生的法律责任、技术风险或经济损失,由使用者自行承担,项目作者不承担任何形式的责任。
  • 禁止滥用: 不得将本项目用于违法牟利、黑产活动或其他不当商业用途。
  • 使用或者参考本项目即视为同意上述条款,即 “谁使用,谁负责” 。如不同意,请立即停止使用并删除本项目。!!!
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/5/21 22:34:25

Java智能地址解析终极指南:企业级架构设计与高性能实现方案

Java智能地址解析终极指南:企业级架构设计与高性能实现方案 【免费下载链接】address-parse Java 版智能解析收货地址 项目地址: https://gitcode.com/gh_mirrors/addr/address-parse 面对电商、物流、外卖等系统中复杂多变的地址输入格式,传统的…

作者头像 李华
网站建设 2026/5/21 22:28:24

【项目实训(个人8)】

继续进行法律文书智能摘要系统的开发,新增了几个功能,并优化了用户体验概述本次开发为法律文书智能摘要系统新增了两项核心功能。其一是摘要版本管理,支持同一文档的多版本摘要生成、存储、对比和回滚。用户在生成摘要时,系统自动…

作者头像 李华
网站建设 2026/5/21 22:26:28

86、【Agent】【OpenCode】bash 工具提示词(完结)

【声明】本博客所有内容均为个人业余时间创作,所述技术案例均来自公开开源项目(如Github,Apache基金会),不涉及任何企业机密或未公开技术,如有侵权请联系删除 背景 上篇 blog 【Agent】【OpenCode】bash 工…

作者头像 李华