3.2 获取API数据
通过3.1节可以知道,API提供了全国3181个城市的天气预报,可以通过互联网在线爬取或读取城市列表,然后通过循环语句一次性获取3181个城市的天气预报。通过阅读文档读取API提供的城市,其城市数量是会变动的,因此最好的方式是直接从网上读取,这样就可以省去人工更新城市列表的工作了。
从网上读取数据的第一步是获取城市列表,然后根据城市列表循环,代码如下。
运行上面这段代码可以提取所有的城市代码,如图3-6所示。
图3-6
上例通过requests.get()方法获取数据,代码如下。
观察打印出来的数据,可以发现并不需要前6行,如图3-7所示。
图3-7
接下来用split()方法将文本转换成列表,再通过一个循环将前6行内容删除。
然后将一大串文本分割出来,这里可以用换行符将每行文本分开。在Python中,\n表示换行符。
删除数据使用的是remove()方法,并且每次都删除第一行(序号为0)数据。因为每次删除第一行数据,所以第二行数据都会变成下一次执行的第一行数据,代码如下。
通过前面的接口信息可以知道,只要获取城市/地区编码就可以了。这里从便捷的角度出发,提取每行的第3~14个字符(由于Python数组是从0开始计数的,因此用2:13表示),共计12个字符,然后通过一个列表元素循环将城市/地区编码打印出来。
完成城市/地区编码的提取后,下一步就是调用接口获取数据,代码如下。
数据是以JSON的格式返回的,每个城市/地区都是一个JSON,如图3-8所示。
这段代码调用了time库,这是为了使用sleep()(睡眠)函数,也就是延时函数。因为API提供了3181个城市/地区的天气预报,这个循环就要执行3181次。为了避免访问服务器过于频繁,保证爬虫的稳定性,这里让程序每次访问后等待1秒钟。在写爬虫的时候不管需要访问的次数是多还是少,最好养成写延时的习惯,延时函数代码如下。
图3-8
如果要将返回的JSON数据解析出来,则可以使用for循环语句。
代码执行结果如图3-9所示。
接下来使用JSON在线结构化的工具观察数据结构。
将其中一个城市的返回数据复制并粘贴到左侧的文本框中,然后单击中间的右三角按钮,就会得到如图3-10所示的结果。通过观察路径可知,3天的天气预报数据在[daily_forecast]路径下,由[0]、[1]和[2]这3个数据节点分别存放3天的天气预报数据,而每天的最高温度在[daily_forecast][n][tmp][max]路径下,其中[n]表示分节点[0]、[1]、[2]。
图3-9
图3-10
如果JSON工具报错,则需要检查复制的内容是否存在多了空格或者少了符号之类的问题,这些都是新手常犯的错误。
requests库返回的数据可以编码成JSON格式的数据,只有JSON对象才适用上面分析的路径,表现方式如下。