【爬虫练习】天气预报查询

利用requests模块爬取中央气象台网站的气象数据,用PySimpleGUI制作简单的交互页面。

一、对网站发送请求

以山西省太原市为例,对应页面网址如下:
http://www.nmc.cn/publish/forecast/ASX/taiyuan.html
而北京朝阳地区,对应页面网址如下:
http://www.nmc.cn/publish/forecast/ABJ/chaoyang.html
我们可以很轻易地发现其中地规律,想查询其他地区时,只要替换加粗部分即可。
获取url之后,就可对网址发送get请求,返回响应数据

url = 'http://www.nmc.cn/publish/forecast/A'+ province + '/' + city + '.html'
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36'
}
page_data = requests.get(url=url, headers=headers)
page_data.encoding = 'utf-8'
page_code = page_data.text

二、获取各类气象数据

通过分析,网站将近七天的气象数据分别存放在七个div标签里,因此可以先将七个div标签里的内容保存到列表中,再遍历列表,获取详细数据
在这里插入图片描述
在单个div标签中,存放有各种气象数据,通过xpath路径即可提取对应数据。需要注意的时,一天的数据分为上午和下午两个部分,如果在下午查询当天的数据,那么上午的气象数据将为空。
在这里插入图片描述
对应代码如下:

tree = etree.HTML(page_code)
div_list = tree.xpath('//*[@id="day7"]/div')    # 获取数据所在<div> </div>
date_w = []
desc_m = []
windd_m = []
winds_m = []
high_tem = []
low_tem = []
desc_e = []
windd_e = []
winds_e = []
for div in div_list:        # 将各项数据定位,保存到对应列表中
    date_w_w = div.xpath('./div/div[1]/text()')[0]
    desc_m_w = div.xpath('./div/div[3]/text()')[0]
    windd_m_w = div.xpath('./div/div[4]/text()')[0]
    winds_m_w = div.xpath('./div/div[5]/text()')[0]
    high_tem_w = div.xpath('./div/div[6]/text()')[0]
    low_tem_w = div.xpath('./div/div[7]/text()')[0]
    desc_e_w = div.xpath('./div/div[9]/text()')[0]
    windd_e_w = div.xpath('./div/div[10]/text()')[0]
    winds_e_w = div.xpath('./div/div[11]/text()')[0]
    date_w.append(date_w_w)
    desc_m.append(desc_m_w)
    windd_m.append(windd_m_w)
    winds_m.append(winds_m_w)
    high_tem.append(high_tem_w)
    low_tem.append(low_tem_w)
    desc_e.append(desc_e_w)
    windd_e.append(windd_e_w)
    winds_e.append(winds_e_w)

三、制作查询交互页面

查询设计流程如下:
1.输入省市信息;
2.选择查询日期;
3.输出查询结果

程序完整代码如下:

import requests
from lxml import etree
import PySimpleGUI as sg
import datetime
# pypinyin库可以把汉字转拼音(未安装此库)
sg.theme('SystemDefaultForReal')    # 设置主题
province = sg.popup_get_text('输入查询省份大写首字母', keep_on_top=True)
city = sg.popup_get_text('输入查询城市拼音', keep_on_top=True)
url = 'http://www.nmc.cn/publish/forecast/A'+ province + '/' + city + '.html'
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36'
}
page_data = requests.get(url=url, headers=headers)
page_data.encoding = 'utf-8'
page_code = page_data.text
# print(page_data)
tree = etree.HTML(page_code)
div_list = tree.xpath('//*[@id="day7"]/div')    # 获取数据所在<div> </div>
date_w = []
desc_m = []
windd_m = []
winds_m = []
high_tem = []
low_tem = []
desc_e = []
windd_e = []
winds_e = []
for div in div_list:        # 将各项数据定位,保存到对应列表中
    date_w_w = div.xpath('./div/div[1]/text()')[0]
    desc_m_w = div.xpath('./div/div[3]/text()')[0]
    windd_m_w = div.xpath('./div/div[4]/text()')[0]
    winds_m_w = div.xpath('./div/div[5]/text()')[0]
    high_tem_w = div.xpath('./div/div[6]/text()')[0]
    low_tem_w = div.xpath('./div/div[7]/text()')[0]
    desc_e_w = div.xpath('./div/div[9]/text()')[0]
    windd_e_w = div.xpath('./div/div[10]/text()')[0]
    winds_e_w = div.xpath('./div/div[11]/text()')[0]
    date_w.append(date_w_w)
    desc_m.append(desc_m_w)
    windd_m.append(windd_m_w)
    winds_m.append(winds_m_w)
    high_tem.append(high_tem_w)
    low_tem.append(low_tem_w)
    desc_e.append(desc_e_w)
    windd_e.append(windd_e_w)
    winds_e.append(winds_e_w)
date_re = []
for i in date_w:        # 删除日期列表中的空格,方便根据日期显示天气
    date_re.append(i.replace(' ', ''))
print(date_re)
print(desc_m)
print(windd_m)
print(winds_m)
print(high_tem)
print(low_tem)
print(desc_e)
print(windd_e)
print(winds_e)

inquire_date = sg.popup_get_text('选择查询日期(支持未来七天):')  # GUI选择日期

ti = datetime.datetime.now()
time_now = str(ti.month) + '月' + str(ti.day) + '日 ' + str(ti.hour) + '时' + str(ti.minute) + '分'
# 日期为今天时,上午和下午的日期显示有所区别(在下午5点以后,网站就不显示当天上午的天气了)
if inquire_date == date_re[0]:
    if ti.hour < 17:
        sg.popup(
                 '城市代码:'+ province + city,
                 '查询时间' + str(time_now),
                 '上午 天气:'+desc_m[0],
                 '上午 风力:'+windd_m[0],
                 '上午 风向:'+winds_m[0],
                 '上午 气温:'+high_tem[0],
                 '下午 气温:'+low_tem[0],
                 '下午 天气:'+desc_e[0],
                 '下午 风向:'+windd_e[0],
                 '下午 风力:'+winds_e[0],
                 font=('黑体',15),
                 keep_on_top=True)
    else:
        sg.popup('城市代码:'+ province + city,
                 '查询时间:'+str(time_now),
                 '下午 气温:'+low_tem[0],
                 '下午 天气:'+desc_e[0],
                 '下午 风向:'+windd_e[0],
                 '下午 风力:'+winds_e[0],
                 font=('黑体',15),
                 keep_on_top=True)
# 日期为其他天时
else:
    date_index = date_re.index(inquire_date)
    sg.popup('城市代码:'+ province + city,
             '查询日期:' + date_re[date_index],
             '上午 天气:' + desc_m[date_index],
             '上午 风力:' + windd_m[date_index],
             '上午 风向:' + winds_m[date_index],
             '上午 气温:' + high_tem[date_index],
             '下午 气温:' + low_tem[date_index],
             '下午 天气:' + desc_e[date_index],
             '下午 风向:' + windd_e[date_index],
             '下午 风力:' + winds_e[date_index],
             font=('黑体', 15),
             keep_on_top=True)

四、实现效果展示

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值