当前位置: 首页 > 后端技术 > Python

Python爬取全国空气质量信息

时间:2023-03-26 17:19:46 Python

主模块requests模块。使用requests模块获取http响应gevent模块。使用gevent开启多个协程来加速爬取re模块或者beautifulsoup模块。我会写正则表达式分析和beautifulsoup分析。.csv模块。用于导出数据到csv文件分析过程1、待抓取页面的URL地址为:http://www.tianqihoubao.com/aqi/。首先访问这个页面(如下图)获取所有citya标签的href属性。知道了各个城市的API之后,就可以爬取各个城市具体的空气质量了。2、打开chrome的debug页面,可以看到a标签在dd标签下,而整个页面,只要a标签没有其他标签,就只在dd标签下。所以在匹配正则表达式或者用BS4找元素的时候,可以先找dd标签,再找下面a标签的href属性。(整个页面只有这里的dd标签,所以要找dd标签)3、找到各个城市的url后,点击查看,发现是月份选择,这里是三月以2020年为例,点击进入。如您所见,我们已经找到了所需的空气质量信息。接下来,让我们看看如何从页面中提取天气信息。4.打开chrome调试工具。可以看到需要的空气质量信息在tr标签下的td标签中,每个tr标签对应一天的空气质量信息,那么可以先搜索tr标签,然后取出空气td标签中的质量信息。(整个页面只有这里有tr标签,所以要找tr标签)代码如下1.先写完整的使用re正则解析的代码。我的思路是:先获取所有城市的a标签中的href属性,然后在url末尾拼接出你要获取的月份。这里获取2020年前三个月的数据,最后启动10个协程,为每个城市新建一个文件,写入抓取的空气质量数据。如果需要将所有文件合并为一个文件,可以执行我单独列出的代码。importtimeimportcsvimportreimportgeventfromgeventimportmonkey,poolmonkey.patch_all()importrequests#storecityurlcity_url=[]#存储要查看的时间范围weather_date=[]#任务列表task_list=[]deffunc(url):"""获取html页面"""response=requests.get(url)#判断请求是否成功ifresponse.status_code!=200:print("Requestfailed")print(response.headers)returnhtml=response.content.decode("gbk")response.close()returnhtmldefget_city_url_list(url):"""Getcityurllist"""try:html=func(url)除了Exceptionase:returncity_list=re.findall(r"

(.*?)
",html,re.S)foriincity_list:#cities=re.findall(r'',i)cities=re.findall(r'(.*?)',i)forjincities:#city_url.append('http://www.tianqihoubao.com'+j)city_url.append(j)defget_day_weather_data(urlname):"""获取每个城市2019年和2020年的差异期间的天气情况存储为一个csv文件urlname:tuple,第一项为url,第二项为namef:filedescriptor"""withopen(r).\January-March2020\%s.csv"%urlname[1],"w",newline='')asf:name=urlname[1]foriinweather_date:new_url=re.sub(r"\.html","-"+i+".html",urlname[0])print(new_url)html=func('http://www.tianqihoubao.com'+new_url)#如果失败,尝试3次#times=0#whiletimes<3:#try:#html=func('http://www.tianqihoubao.com'+new_url)#break#exceptExceptionase:#time.sleep(2)#times+=1#iftimes==3:#returnrow_list=re.findall(r"(.*?)",html,re.S)forjinrow_list[1:]:aqi_data=re.findall(r"\s*(.*?)\s*",j,re.S)#2.根据文件对象构造csv写入对象csv_writer=csv.writer(f)csv_writer.writerow([name]+aqi_data)if__name__=="__main__":get_city_url_list("http://www.tianqihoubao.com/aqi/")#print(city_url)#foriincity_url[41:]:#print(i)#处理标签变成201903这样的格式date_list=[str(i)foriinrange(1,4)]foriindate_list:iflen(i)<2:i="0"+iweather_date.append("2020"+i)#print(weather_date)#withopen(r"NationalCityWeather2.csv","w")asf:#foriincity_url:#get_day_weather_data(i,f)#多个协程生成csv文件task_pool=pool.Pool(10)foriincity_url:task_pool.apply_async(get_day_weather_data,args=(i,))task_pool.join()importos#IfIf你需要把所有的文件合并成一个,执行这段代码path):对于文件名中的文件名:print()pathnames+=[os.path.join(path,filename)]print(pathnames)withopen(r".\weather_data_202001-03.csv","w")asf:foriinpathnames:withopen(i,"r")asg:data=g.read()f.write(data)2.后来我我又学习了beautulsoup模块,解析html页面很简单,我写的捕获a标签href属性部分的代码如下:#http://www.tianqihoubao.com/aqi/withopen("123.html","r")asf:soup=BeautifulSoup(f,"html.parser")#查找所有dd标签l1=soup.find_all('dd')foriinl1:#查找每个标签下的所有a标签ddtagl2=i.find_all('a')forjinl2:#打印出每个a标签的href属性print(j['href'])3.最后说说我对这两个模块的感受re和beautifulsoup的,我比较习惯用re模块,re给我的感觉虽然写起来有点难,但是抓数据的时候想抓哪里就抓哪里,爬的时候去掉这些,但是beautifulsoup我还没找到更好的方法,大家可以自己试试,如果对代码部分有疑问,可以直接在文章下方评论,我看到会第一时间回复。