python爬取天气预报数据,并实现数据可视化

一、前言

在爬取数据时,有些数据,如图片、视频等等,爬到就是赚到;而有时候,我们爬到的可能只是一些数字,表面上,看上去没什么意义,但当我们换一种角度来看待问题的话,可能又是一个崭新的世界。于是,我今天学习了一下数据的可视化。

二、爬取目标及结果展示

由于是我第一次尝试可视化,我选了一个简单的方向----爬取天气预报
然后我就在百度上,随便搜了一下,直接准备爬取第一个。
网址链接:北京的天气

结果如下:
在这里插入图片描述

三、页面分析

在这里插入图片描述
进入页面之后,我分别看了“7天”、“8-15天”、“40天”,发现,上方链接是一直变化的。但是当我去检测页面的时候,发现了了不得的东西。
在这里插入图片描述
哎哟,我去,这不就是上方的链接变化嘛。

于是我们就可以通过手段直接拿到“详情页的传送链接”了。
在这里插入图片描述
假设这时候,我们已经拿到了“7天”和“8-15天”的链接了。
对比一下,两个页面的内容。

7天:
在这里插入图片描述
8-15天:
在这里插入图片描述
哎哟,我去,两个页面的排版居然不一样,那网页源代码也肯定不一样咯。

在这里插入图片描述
仔细看之后,发现还好,只有两个地方,稍微需要处理一下。

①:“7天”里的风向

(你可以说东风转东南风,但你不能说是东南风转东南风吧)

②:“7天”和“8-15天”的气温
你会发现它是这个样子:
在这里插入图片描述
甚至这个样子:
在这里插入图片描述
但是不用害怕,我已经解决啦,哈哈哈哈哈。

详情见代码部分,基本上每行都有注释

四、完整代码

fake_useragent库的使用教程:Python爬虫有用的库:fake_useragent,自动生成请求头

# -*- coding: UTF-8 -*-
"""
@Author  :远方的星
@Time   : 2021/2/28 10:20
@CSDN    :https://blog.csdn.net/qq_44921056
@腾讯云   : https://cloud.tencent.com/developer/column/91164
"""
import requests
from lxml import etree
from fake_useragent import UserAgent
import pandas as pd
from matplotlib import pyplot as plt

# 随机产生请求头
ua = UserAgent(verify_ssl=False, path='fake_useragent.json')


# 获取七天和八到十五天的页面链接
def get_url(url):
    response = requests.get(url=url).text
    html = etree.HTML(response)
    url_7 = 'http://www.weather.com.cn/' + html.xpath('//*[@id="someDayNav"]/li[2]/a/@href')[0]
    url_8 = 'http://www.weather.com.cn/' + html.xpath('//*[@id="someDayNav"]/li[3]/a/@href')[0]
    return url_7, url_8


# 获取未来七天天起预报数据
def get_data_1(url):
    response = requests.get(url=url)
    response.encoding = "utf-8"  # 防止乱码,进行编码
    response = response.text
    html = etree.HTML(response)
    list_s = html.xpath('//*[@id="7d"]/ul/li')
    # 提前定义五个空列表用于存放信息
    data, weather, x, y, wind_scale = [], [], [], [], []
    temperature = []  # 定义一个空列表,用于处理最低气温和最高气温的合并
    wind = []  # 定义一个空列表,用于存放风向
    high, low = [], []  # 定义两个空列表,用于存放未处理的最高、最低气温,为绘图做铺垫
    for i in range(len(list_s)):
        a = list_s[i].xpath('./h1/text()')  # 获取日期
        b = list_s[i].xpath('./p[1]/text()')  # 获取天气情况
        c = list_s[i].xpath('./p[2]/span/text()')  # 获取最高气温
        d = list_s[i].xpath('./p[2]/i/text()')  # 获取最低气温
        g = list_s[i].xpath('./p[3]/i/text()')  # 获取风级
        data.append(''.join(a))  # 集中日期
        weather.append(''.join(b))  # 集中天气情况
        high.append(''.join(c))  # 集中最高气温
        low.append(''.join(d))  # 集中最低气温
        x.append(''.join(c))  # 集中最高气温
        x.append('/')  # 加入一个分隔符
        x.append(''.join(d))  # 集中最低气温
        temperature.append(''.join(x[0:3]))  # 把最高气温和最低气温合并
        wind_scale.append(''.join(g))  # 集中风级
        f = list_s[i].xpath('./p[3]/em/span/@title')  # 获取风向
        if f[0] == f[1]:  # 条件语句,用于判断两个风向是否一致,进而做出一定反应
            wind.append(''.join(f[0]))
        else:
            y.append(''.join(f[0]))
            y.append('转')
            y.append(''.join(f[1]))
            wind.append(''.join(y[0:3]))
    excel = pd.DataFrame()  # 定义一个二维表
    excel['日期'] = data
    excel['天气'] = weather
    excel['气温'] = temperature
    excel['风向'] = wind
    excel['风级'] = wind_scale
    excel['最高气温'] = high
    excel['最低气温'] = low
    return excel


# 获取8-15天天气预报数据
def get_data_2(url):
    response = requests.get(url=url)
    response.encoding = "utf-8"  # 防止乱码,进行编码
    response = response.text
    html = etree.HTML(response)
    list_s = html.xpath('//*[@id="15d"]/ul/li')
    # 提前定义五个空列表用于存放信息
    data, weather, a, wind, wind_scale = [], [], [], [], []
    temperature = []  # 定义一个空列表,用于处理最低气温和最高气温的合并
    high, low = [], []  # 定义两个空列表,用于存放未处理的最高、最低气温,为绘图做铺垫
    for i in range(len(list_s)):
        data_s = list_s[i].xpath('./span/text()')  # data_s[0]是日期,data_s[1]是天气,data_s[2]是最低气温,data_s[3]是风向,data_s[4]是风级
        b = list_s[i].xpath('./span/em/text()')  # 获得最高气温
        data.append(''.join(data_s[0]))  # 集中日期
        weather.append(''.join(data_s[1]))  # 集中天气
        wind.append(''.join(data_s[3]))  # 集中风向
        wind_scale.append(''.join(data_s[4]))  # 集中风级
        high.append(''.join(b))  # 集中最高气温
        low.append(''.join(data_s[2]))  # 集中最低气温
        a.append(''.join(b))  # 集中最高气温
        a.append(''.join(data_s[2]))  # 集中最低气温(这时最高气温已经在a列表里了)
        temperature.append(''.join(a[0:2]))  # 集中最低+最高气温
    excel = pd.DataFrame()  # 定义一个二维表
    excel['日期'] = data
    excel['天气'] = weather
    excel['气温'] = temperature
    excel['风向'] = wind
    excel['风级'] = wind_scale
    excel['最高气温'] = high
    excel['最低气温'] = low
    return excel


# 实现数据可视化
def get_image(data, high, low):
    # 用来正常显示中文标签
    plt.rcParams['font.sans-serif'] = ['SimHei']
    # 用来正常显示负号
    plt.rcParams['axes.unicode_minus'] = False
    # 根据数据绘制图形
    fig = plt.figure(dpi=128, figsize=(10, 6))
    plt.plot(data, high, c='red', alpha=0.5)
    plt.plot(data, low, c='blue', alpha=0.5)
    # 给图表中两条折线中间的部分上色
    plt.fill_between(data, high, low, facecolor='blue', alpha=0.2)
    # 设置图表格式
    plt.title('北京近15天天气预报', fontsize=24)
    plt.xlabel('日期', fontsize=12)
    # 绘制斜的标签,以免重叠
    fig.autofmt_xdate()
    plt.ylabel('气温', fontsize=12)
    # 参数刻度线设置
    plt.tick_params(axis='both', which='major', labelsize=10)
    # 修改刻度
    plt.xticks(data[::1])
    # 显示图片
    plt.show()


def main():
    url = 'http://www.weather.com.cn/weather1d/101010100.shtml'
    url_7, url_8 = get_url(url)
    data_1 = get_data_1(url_7)
    data_2 = get_data_2(url_8)
    data_s = pd.concat([data_1, data_2], axis=0)
    data_s['最高气温'] = data_s['最高气温'].map(lambda z: int(z.replace('℃', '')))
    data_s['最低气温'] = data_s['最低气温'].map(lambda z: int(z.replace('℃', '').replace('/', '')))
    # print(type(data_s))
    # print(type(data_s['最高气温']))   # 有兴趣的小伙伴,可以看一下这里的类型分析嗷,这两个数据是不一样哒
    data = data_s['日期']
    high = data_s['最高气温']
    low = data_s['最低气温']
    get_image(data, high, low)


if __name__ == '__main__':
    main()

五、补充

第一次使用可视化,代码可能出现冗余的地方,希望大佬给些指点呀。

六、不足(经读者反馈)

有小伙伴在运行代码的情况时,出现了list index out of range的错误,一开始我以为是他的问题,后来我写另外一篇文章时,调试了三四天,发现,应该是我的问题。因为这个网站晚上时,会更改一点点结构,爬取的时候,会出现一个空列表。那怎么解决呢?在气温那里使用条件语句,把列表为空的情况排除掉即可。
我今天更新的一个文章,依然用的这个网页链接,已经使用if条件语句进行排除空列表。

文章传送门

作者:远方的星
CSDN:https://blog.csdn.net/qq_44921056
腾讯云:https://cloud.tencent.com/developer/column/91164
本文仅用于交流学习,未经作者允许,禁止转载,更勿做其他用途,违者必究。

### 回答1: Python是一种简单易学的编程语言,适合数据处理和分析。在爬取天气数据方面,Python有很多强大的第三方库可以帮助我们完成这项任务。 首先,我们可以使用BeautifulSoup库或Scrapy爬取天气网站上的数据。这些库可用于将HTML网页转换为Python对象,从而轻松地提取数据。 然后,我们可以使用pandas库将爬取数据存储在DataFrame中,并对其进行有效的处理和分析。pandas提供了各种数据操作方法,例如连接、过滤、排序和分组,使我们能够有效的清理和整理数据。 最后,我们可以使用matplotlib或Seaborn等可视化库来创建数据可视化图表。这些库提供了各种绘图选项,例如折线图、散点图等,使我们能够更好地理解和分析数据。 总结来说,从爬取到处理再到可视化分析,Python提供了完整的工具链,使我们可以轻松地获取所需信息、分析数据并推出结论。 ### 回答2: Python是一门非常适合进行数据爬取数据分析的语言。如果想要实现爬取天气数据并进行可视化分析,可以使用Python的第三方库进行实现。下面我们来详细介绍一下具体的步骤。 首先,我们需要选择合适的天气数据来源。在国内,有很多天气网站提供了API接口供开发者使用。例如,中国天气网、天气之子等等。我们可以选择其中一个合适的接口进行数据爬取。比如,我们可以爬取每天的温度、湿度、风力等信息,并将其存储到本地的数据库中或者保存为csv、txt等格式的文件。 接下来,我们需要将爬取到的天气数据进行可视化分析。这里我们可以使用Python的matplotlib库,它是一个非常强大的数据可视化工具。我们可以通过调用该库中的函数,绘制出各种类型的图表,如折线图、柱状图、散点图等等。具体的绘图方法,可以根据我们需要展示的信息以及分析目的,灵活选择。 最后,我们可以将经过可视化分析的数据图表进行可视化展示。Python提供了很多可视化库,比如Flask、Django等,可以将分析结果以Web页面的形式展现出来。另外,还可以使用Jupyter Notebook进行编程和可视化的交互式展示。 总之,通过Python进行天气数据爬取可视化分析,可以帮助我们更加全面、直观地了解天气情况,并从中发现有用的规律和趋势。而本文所提到的方法只是其中的一种,还有很多其他的可视化工具和数据分析思路,需要根据具体情况进行选择和应用。 ### 回答3: Python 是一种非常强大的编程语言,可用于爬取数据可视化分析。在这里,我们将介绍如何使用 Python 爬取天气数据,并对其进行可视化分析。 1. 爬取天气数据 爬取天气数据的第一步是确定数据源。一些常见的数据源包括:天气预报和气象站数据。我们可以使用 Python 程序访问这些数据源,然后将其存储在 CSV 文件中。 以下是使用 Python 爬取天气数据的简单步骤: - 导入所需的库:如requests、beautifulsoup4、csv等库; - 定义爬取的网址:通过查看天气预报或气象站来确定要爬取的网址; - 解析网页:使用BeautifulSoup库来解析HTML源代码; - 提取数据:从HTML源代码中提取所需信息(例如,温度、湿度、气压等); - 存储数据:利用Python的csv库将提取的数据存储在CSV文件中。 2. 可视化分析 Python还提供了各种库和工具,可对爬取的天气数据进行可视化分析。下面是一些常用的库和工具: - Matplotlib:用于绘制图表和可视化; - Pandas:用于加载和预处理数据; - Seaborn:用于数据可视化和统计; - Plotly:用于交互式绘图; - Bokeh:用于高级交互式可视化可视化分析的步骤如下: - 导入所需的库; - 加载数据:从CSV文件中加载爬取的天气数据; - 预处理数据:通过排序、过滤和合并数据等方式,为可视化做准备; - 绘图:根据需要,使用Matplotlib、Seaborn、Plotly和Bokeh等库来绘制图表; - 交互:使用Plotly和Bokeh等库创建交互式可视化。它们提供了各种控件,例如滑块、下拉菜单、复选框和单选按钮,以便用户能够自定义图表。 总之,使用Python爬取天气数据并进行可视化分析是一项有用的技能,使您能够更好地理解天气变化和趋势。
评论 29
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱打瞌睡的CV君

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值