【Python爬虫实战入门】:全球天气信息爬取

文章目录

      • 一、爬取需求
      • 二、所需第三方库
        • 2.1 简介
      • 三、实战案例
      • 四、完整代码

一、爬取需求

目标网站http://www.weather.com.cn/textFC/hb.shtml
需求:爬取全国的天气(获取城市以及最低气温)
目标urlhttp://www.weather.com.cn/textFC/hz.shtml

二、所需第三方库

requests
BeautifulSoup4

安装

requestspip install requests -i https://pypi.tuna.tsinghua.edu.cn/simple some-package
BeautifulSoup4pip install BeautifulSoup4 -i https://pypi.tuna.tsinghua.edu.cn/simple some-package

2.1 简介

requests模块

官方文档https://requests.readthedocs.io/projects/cn/zh-cn/latest/
requests 是 Python 编程语言中一个常用的第三方库,它可以帮助我们向 HTTP 服务器发送各种类型的请求,并处理响应。

  • 向 Web 服务器发送 GET、POST 等请求方法;
  • 在请求中添加自定义标头(headers)、URL 参数、请求体等;
  • 自动处理 cookies;
  • 返回响应内容,并对其进行解码;
  • 处理重定向和跳转等操作;
  • 检查响应状态码以及请求所消耗的时间等信息。

BeautifulSoup4模块

官方文档https://www.crummy.com/software/BeautifulSoup/bs4/doc.zh/
Beautiful Soup 是一个 可以从 HTML 或 XML 文件中提取数据的 Python 库。它能用你喜欢的解析器和习惯的方式实现 文档树的导航、查找、和修改。

下表描述了几种解析器的优缺点:
在这里插入图片描述
注意:如果一段文档格式不标准,那么在不同解析器生成的 Beautiful Soup 数可能不一样。 查看 解析器之间的区别 了解更多细节。

数据提取之CSS选择器

  • 熟悉前端的同学对 css 选择器一定不会陌生,比如 jquery 中通过各种 css 选择器语法进行 DOM 操作等
  • 学习网站http://www.w3cmap.com/cssref/css-selectors.html

在爬虫中使用css选择器,代码教程

>>> from requests_html import session# 返回一个Response对象
>>> r = session.get('https://python.org/')# 获取所有链接
>>> r.html.links
{'/users/membership/', '/about/gettingstarted/'}# 使用css选择器的方式获取某个元素
>>> about = r.html.find('#about')[0]>>> print(about.text)
About
Applications
Quotes
Getting Started
Help
Python Brochure

三、实战案例

目标网站:http://www.weather.com.cn/textFC/hb.shtml

思路分析:

  1. 通过find方法,定位的div class=conMidtab2
  2. 通过find_all方法,找所有的tr标签

函数功能

  1. 得到网页源码
  2. 解析数据
  3. 保存数据
  4. 主函数

程序框架

import requests
from bs4 import BeautifulSoup
# 获取网页源码
def get_html():pass
# 解析数据
def parse_html():pass
# 保存数据
def save_data():pass
# 主函数
def main():pass

获取网页源码
在主函数中进行传参调用

# 获取网页源码
def get_html(url):html = requests.get(url)html.encoding = 'utf-8'# print(html.text)return html.text# 主函数
def main():url = 'http://www.weather.com.cn/textFC/hz.shtml'html = get_html(url)
main()

解析数据
get_html函数的返回值(网页源码)作为参数传给parse_html函数

# 主函数
def main():url = 'http://www.weather.com.cn/textFC/hz.shtml'html = get_html(url)parse_html(html)
main()

对于parse_html函数,要将传入的网页源码进行解析,获取我们想要的数据。
在这里插入图片描述
通过观察元素,每一个class="conMidtab2"的div标签就代表一个省份,那么他的父级元素class="conMidtab"的div标签就包含三个省份的天气信息,了解了这些,剩下的我们只需要根据元素之间的关系,一步步提取我们想要的数据即可。

# 解析数据
def parse_html(html):# 创建对象soup = BeautifulSoup(html, 'lxml')conMidtab = soup.find('div', class_="conMidtab")tables = conMidtab.find_all('table')# print(tables)for table in tables:trs = table.find_all('tr')[2:]# print(trs)for index, tr in enumerate(trs):tds = tr.find_all('td')# print(tds)city = list(tds[1].stripped_strings)[0]  # 城市temp = tds[-2].string  # 最低气温print(city, temp)break

在这里插入图片描述
但是,这里出现了一个问题,那就是我们要打印城市信息的时候,只能打印出第一个城市,后面的城市无法打印出来,通过查看元素后我们会发现,除了第一个城市是在第二个td标签里面,其余城市都在第一个td标签里面,所以在这里我们要将循环改一下,同时还要加一个判断,只要是第一个城市就去第二个td标签,其余的取第一个td标签
在这里插入图片描述
想要实现这种效果,我们就要用到一个函数enumerate,这个函数可以将下标和下标对应的值给显示出来。

# 解析数据
def parse_html(html):# 创建对象soup = BeautifulSoup(html, 'lxml')conMidtab = soup.find('div', class_="conMidtab")tables = conMidtab.find_all('table')# print(tables)for table in tables:trs = table.find_all('tr')[2:]# print(trs)for index, tr in enumerate(trs):tds = tr.find_all('td')# print(tds)if index == 0:  # 第一个城市取第二个td标签city = list(tds[1].stripped_strings)[0]  # 城市else:  # 其余的取第一个td标签city = list(tds[0].stripped_strings)[0]  # 城市temp = tds[-2].string  # 最低气温print(city, temp)

在这里插入图片描述
更换url查看数据信息
在主函数里面去更换url,然后查看打印的数据信息是否正确。运行后发现前面的都是正确的,直到更换到港澳台1地区时就出现了问题。

# 主函数
def main():# url = 'http://www.weather.com.cn/textFC/hz.shtml'  # 华中地区# url = 'http://www.weather.com.cn/textFC/hb.shtml'  # 华北地区url = 'http://www.weather.com.cn/textFC/gat.shtml'  # 港澳台地区html = get_html(url)parse_html(html)
main()

在这里插入图片描述
在这里插入图片描述
我们发现,我们无法在元素中发现问题,那么我们现在就应该查看一下网页源代码。
在这里插入图片描述
查看网页源代码之后可以发现,他所在的table标签是没有结束标签的,后面的城市的table标签也没有结束标签,这也就导致了数据混乱。
想要解决这个问题,就需要更换一下解析器。上面在提到BeautifulSoup4时的解析器,我们发现html5lib这个解析器拥有最好的容错性。
在这里插入图片描述
下载pip install html5lib

# 解析数据
def parse_html(html):# 创建对象soup = BeautifulSoup(html, 'html5lib')  # 将lxml换成html5libconMidtab = soup.find('div', class_="conMidtab")tables = conMidtab.find_all('table')# print(tables)for table in tables:trs = table.find_all('tr')[2:]# print(trs)for index, tr in enumerate(trs):tds = tr.find_all('td')# print(tds)if index == 0:  # 第一个城市取第二个td标签city = list(tds[1].stripped_strings)[0]  # 城市else:  # 其余的取第一个td标签city = list(tds[0].stripped_strings)[0]  # 城市temp = tds[-2].string  # 最低气温print(city, temp)

在这里插入图片描述
页面切换
要实现页面切换首先我们要观察一下不同页面的url

华北:http://www.weather.com.cn/textFC/hb.shtml
东北:http://www.weather.com.cn/textFC/db.shtml
华南:http://www.weather.com.cn/textFC/hn.shtml
华中:http://www.weather.com.cn/textFC/hz.shtml
港澳台:http://www.weather.com.cn/textFC/gat.shtml

我们发现,这些url的不同之处就在于后面的字母的不同,而这些字母又恰好是地区的首字母,那么我们只需要将这些地区的首字母存入到一个列表当中,循环之后就可以实现页面的切换。

# 主函数
def main():district = ['hb', 'db', 'hd', 'hz', 'hn', 'xb', 'xn', 'gat']# url = 'http://www.weather.com.cn/textFC/hz.shtml'# url = 'http://www.weather.com.cn/textFC/hb.shtml'for dist in district:url = f'http://www.weather.com.cn/textFC/{dist}.shtml'html = get_html(url)parse_html(html)
main()

数据保存
定义一个全局变量的列表list_data,在解析数据的第二层循环中定义一个字典,将城市和最低气温添加到字典中去,最后将字典添加到list_data列表中。

# 保存数据
def save_data():with open('全国天气.csv', 'w', encoding='utf-8-sig', newline='') as f:writer = csv.DictWriter(f, fieldnames=('城市', '最低气温'))writer.writeheader()writer.writerows(list_data)

在这里插入图片描述

四、完整代码

import requests
from bs4 import BeautifulSoup
import csvlist_data = []
# 获取网页源码
def get_html(url):html = requests.get(url)html.encoding = 'utf-8'# print(html.text)return html.text# 解析数据
def parse_html(html):# 创建对象soup = BeautifulSoup(html, 'html5lib')  # 将lxml换成html5libconMidtab = soup.find('div', class_="conMidtab")tables = conMidtab.find_all('table')# print(tables)for table in tables:trs = table.find_all('tr')[2:]# print(trs)for index, tr in enumerate(trs):dic = {}tds = tr.find_all('td')# print(tds)if index == 0:  # 第一个城市取第二个td标签city = list(tds[1].stripped_strings)[0]  # 城市else:  # 其余的取第一个td标签city = list(tds[0].stripped_strings)[0]  # 城市dic['城市'] = citytemp = tds[-2].string  # 最低气温dic['最低气温'] = templist_data.append(dic)# 保存数据
def save_data():with open('全国天气.csv', 'w', encoding='utf-8-sig', newline='') as f:writer = csv.DictWriter(f, fieldnames=('城市', '最低气温'))writer.writeheader()writer.writerows(list_data)# 主函数
def main():district = ['hb', 'db', 'hd', 'hz', 'hn', 'xb', 'xn', 'gat']# url = 'http://www.weather.com.cn/textFC/hz.shtml'# url = 'http://www.weather.com.cn/textFC/hb.shtml'for dist in district:url = f'http://www.weather.com.cn/textFC/{dist}.shtml'html = get_html(url)parse_html(html)save_data()  # 数据保存main()

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/832971.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

项目计划书(Word原件)

项目开发计划包括项目描述、项目组织、成本预算、人力资源估算、设备资源计划、沟通计划、采购计划、风险计划、项目过程定义及项目的进度安排和里程碑、质量计划、数据管理计划、度量和分析计划、监控计划和培训计划等。 软件资料清单列表部分文档: 工作安排任务书…

人脸采集训练识别

项目概述: 本地摄像头采集人脸数据集,通过训练得到trainingData.yml模型,加载haarcascade_frontalface_default.xml实现人脸识别。haarcascade_frontalface_default.xml 文件并不是一个完整的人脸识别模型,而是一个用于检测正脸&a…

Llama3-Tutorial之XTuner微调Llama3图片理解多模态

Llama3-Tutorial之XTuner微调Llama3图片理解多模态 基于 Llama3-8B-Instruct 和 XTuner 团队预训练好的 Image Projector 微调自己的多模态图文理解模型 LLaVA。 参考: https://github.com/SmartFlowAI/Llama3-Tutorial 1. 环境、模型、数据准备 1.1 配置环境 使用如…

Linux命令:watch命令

目录 1 watch命令1.1 简介1.2 说明1.3 案例1、重复执行uptime命令2、显示两次命令执行结果差异3、只想查看smile用户的文件4、每隔 n s执行一次命令 总结 1 watch命令 1.1 简介 watch 是一个在 Unix 和 Unix-like 系统(包括 Linux 和 macOS)中常用的命…

【算法】双指针

下面是对双指针算法的题目总结和归纳,有需要借鉴即可。 双指针算法习题目录 1.移动零2.复写零3.快乐数4.盛最多水的容器5.有效三角形的个数6.和为s的两个数7.三数之和8.四数之和 1.移动零 题目链接:LINK 题解: 思路①:暴力求解 …

大宋咨询消费者需求研究问卷如何设计

设计消费者需求研究问卷需要考虑清楚研究目标、问题和目标受众的特点。一个良好的问卷设计能够确保收集到准确、有用的消费者反馈。以下大宋咨询是设计消费者需求研究问卷的一些建议: 1. 确定研究目标和问题: 在设计问卷之前,明确你希望从问…

【备战软考(嵌入式系统设计师)】08 - 多媒体技术信息安全

多媒体技术 这内容比较杂,而且跟咱嵌入式的关系不大,但是软考里会考一些,下面我就结合我已经刷过的一千多道往年真题概括总结一下常考的知识点。 媒体分类 首先媒体分为五类: 感觉媒体,让人直接感觉得到的媒体&…

Java Solon v2.7.6 发布

Java Solon 是什么框架? Java “新的”应用开发框架。开放原子开源基金会,孵化项目。从零开始构建(非 java-ee 架构),有灵活的接口规范与开放生态。 追求: 更快、更小、更简单提倡: 克制、简洁…

zTasker v1.88.1一键定时自动化任务

软件介绍 zTasker是一款完全免费支持定时、热键或条件触发的方式执行多种自动化任务的小工具,支持win7-11。其支持超过100种任务类型,50种定时/条件执行方法,而且任务列表可以随意编辑、排列、移动、更改类型,支持任务执行日志&a…

人脸美妆SDK解决方案,自研人脸美妆方案

美妆已经成为视频内容中不可或缺的一部分。从拍摄到编辑,再到直播,美妆效果都能为视频内容增添魅力,吸引更多观众的眼球。为了满足企业对于高质量美妆效果的需求,美摄科技凭借多年的技术积累和创新精神,推出了全新的人…

基于Spring EL表达式处理业务表达式

文章目录 简介Spring EL的常见应用Value处理注解xml中使用 Spring EL表达式基本表达式模板函数表达式 Spring EL定制引用Spring的bean 简介 SpringEL是Spring表达式,功能非常强大。 我们可以能在Value、Cachable、自定义注解中的应用EL表达式,当然这些…

子集II(力扣90)

解题思路&#xff1a;used判断是否出现过&#xff0c;然后遍历就好了 具体代码如下&#xff1a; class Solution { public: vector<vector<int>>result; vector<int>path; void travelBack(vector<int>&nums,int startIndex,vector <bool&…

内容安全(DPI和DFI解析)

内容安全前言&#xff1a; 防火墙的本质其实就是包过滤&#xff0c;我们通常所说的安全设备&#xff08;如&#xff1a;IPS、IDS、AV、WAF&#xff09;的检测重心是应用层。下一代防火墙基于传统防火墙的拓展能力&#xff0c;就是可以将以上的安全设备模块集成在一起&#xff0…

智慧应急三维电子沙盘系统

深圳易图讯科技有限公司&#xff08;www.3dgis.top&#xff09;自主研发的智慧应急三维电子沙盘系统依托大数据融合物联网、云计算、移动互联、5G、BIM、三维GIS等新一代信息技术&#xff0c;集成了高清卫星影像、地形数据、实景三维模型、现场环境数据、物联感知信息、人口、建…

Java作业8-泛型和模板类

编程1 题目 自定义堆栈类 用泛型数组实现自定义堆栈类GenericStack&#xff0c;可处理任意类型数据。 堆栈类中包含三个成员&#xff0c;一为泛型类型数组list&#xff0c;保存栈中元素&#xff0c;一为整型成员length表示数组的长度&#xff0c;一为整型成员count表示当前…

SRC公益漏洞挖掘思路分享

0x00 前言 第一次尝试挖SRC的小伙伴可能会觉得挖掘漏洞非常困难&#xff0c;没有思路&#xff0c;不知道从何下手&#xff0c;在这里我分享一下我的思路 0x01 挖掘思路 确定自己要挖的漏洞&#xff0c;以及该漏洞可能存在的功能点&#xff0c;然后针对性的进行信息收集 inurl…

LeetCode 每日一题 ---- 【741.摘樱桃】

LeetCode 每日一题 ---- 【741.摘樱桃】 741.摘樱桃方法&#xff1a;动态规划 741.摘樱桃 方法&#xff1a;动态规划 这是一道动态规划的题目&#xff0c;enmmmm&#xff0c;依旧是做不出来&#xff0c;尤其是看到困难两个标红的字体&#xff0c;就更不想做了&#xff0c;然后…

一起深度学习(AlexNet网络)

AlexNet神经网络 代码实现&#xff1a; 代码实现&#xff1a; import torch from torch import nn from d2l import torch as d2lnet nn.Sequential(# 采用了11*11的卷积核来捕捉对象&#xff0c;因为原始输入数据比较大#步幅为4 &#xff0c;可减少输出的高度核宽度。#输出通…

【算法刷题day41】Leetcode:343. 整数拆分、96. 不同的二叉搜索树

文章目录 Leetcode 343. 整数拆分解题思路代码总结 Leetcode 96. 不同的二叉搜索树解题思路代码总结 草稿图网站 java的Deque Leetcode 343. 整数拆分 题目&#xff1a;343. 整数拆分 解析&#xff1a;代码随想录解析 解题思路 通过两轮循环&#xff0c;分别找到每个数的最大…

FineReport高频面试题及参考答案

FineReport是一款利用什么语言开发的报表工具&#xff1f; FineReport是一款基于Java语言开发的报表工具。Java是一种广泛使用的编程语言&#xff0c;特别适合于跨平台的软件开发。FineReport利用Java语言的诸多优势&#xff0c;如稳定性、安全性、可移植性和强大的网络功能&a…