美文网首页PythonPython爬虫作业
Python 爬取天气网及3种数据储存方式(MySQL / Mo

Python 爬取天气网及3种数据储存方式(MySQL / Mo

作者: 高杆python | 来源:发表于2017-06-04 18:44 被阅读1554次

    今天完成整理一篇学习笔记,有关BeatifulSoup和XPath使用比较。但是由于刚刚学习爬虫不久,许网页元素定位获取的方法和技巧还没有完全掌握,所以今天先按照自己的节奏跳过这篇作业,继续完成爬虫实战,等到对BeatifulSoup和XPath使用熟练后,再做一次深入详细的总结笔记。今天虽然不比较BeatifulSoup和XPath,但是我会在爬取中国天气网数据后,对爬取数据的三种储存方式(MySQL数据库、Mongo数据库和CSV文件)进行简单的比较。
    1.作业要求:爬取中国天气网 你所在城市过去一年的历史数据
    中国天气网URL:http://www.weather.com.cn/forecast/
    2.思路分析:
    中国天气网的数据是JS异步加载返回的,需要抓包获取数据,抓包后返回的数据结构是JSON形式,可以直接采用Python的json库中的json.loads()函数进行反序话转换成字典类型进行处理,具体分析步骤如图:
    (1)具体获取数据的网址:http://www.weather.com.cn/weather40d/101060201.shtml

    中国天气网获取数据网页

    (2)点击切换月份按钮,查看不同月份天气,发现网页URL没有变化,判断为js异步加载数据


    网页URL.png

    (3)按F12查看Network,点击切换月份,发现每次点击都有新的js加载出现:


    F12-Network.png

    (4)分别查看动态加载的js的Headers和Response查看请求的URL规律和返回值。发现日期的变化包含在Request Url中,返回值即为json格式的天气数据。


    Headers_Resquest url.png
    Response.png

    (5)Copy as cURL使用Postman发送请求测试,发现Headers中不携带Referer将返回403拒绝访问,所以在Headers请求中需携带Referer。


    Copy as cURL.png Postman请求测试.png

    (6)程序代码1(存储到MySQL数据库):

    import requests
    import json
    import pymysql
    class WeatherSpider(object):
        connect = pymysql.connect(
            host='localhost', 
            user='root', 
            passwd='root',  
            db='test',  
            port=3306,  
            charset='utf8'
            )
        cursor = connect.cursor()
        def __inti__(self):
            pass
        def request(self,url):
            #请求头(不带Referer将返回403,用Postman测试)
            headers = {
            'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36',
            'Referer': 'http://www.weather.com.cn/weather40d/101060201.shtml'
            }
            return requests.get(url,headers=headers)
        def create_url(self):
            year = '2016'
            for i in range(1,13):
                month = str(i) if i > 9 else "0" + str(i)
                url = "http://d1.weather.com.cn/calendar_new/" + year + "/101060201_" + year + month + ".html"
                self.get_data(url)
            #关闭数据库链接,释放资源
            self.connect.close()
        def get_data(self,url):
            respone = self.request(url).content
            json_str = respone.decode(encoding='utf-8')[11:]
            weathers = json.loads(json_str)
            for weather in weathers:
                self.cursor.execute("use test")
                self.cursor.execute("insert into jilin_weather_tbl (date,week,hmax,hmin,hgl) values(%s,%s,%s,%s,%s)",(weather.get('date'),'星期'+weather.get('wk'),weather.get('hmax'),weather.get('hmin'),weather.get('hgl'))) 
                self.connect.commit()
    if __name__ == '__main__':
        jl_weather = WeatherSpider()
        jl_weather.create_url()
    

    实现效果图:


    存入MySQL数据库.png

    (7)程序代码2(存储到Mongo数据库)

    import requests
    import json
    import pymongo
    class WeatherSpider(object):
        client = pymongo.MongoClient('localhost', 27017)
        mydb = client['mydb']
        jilin_weather = mydb['jilin_weather']
        def __inti__(self):
            pass
        def request(self,url):
            #请求头(不带Referer将返回403,用Postman测试)
            headers = {
            'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36',
            'Referer': 'http://www.weather.com.cn/weather40d/101060201.shtml'
            }
            return requests.get(url,headers=headers)
        def create_url(self):
            year = '2016'
            for i in range(1,13):
                month = str(i) if i > 9 else "0" + str(i)
                url = "http://d1.weather.com.cn/calendar_new/" + year + "/101060201_" + year + month + ".html"
                self.get_data(url)
        def get_data(self,url):
            respone = self.request(url).content
            json_str = respone.decode(encoding='utf-8')[11:]
            weathers = json.loads(json_str)
            for weather in weathers:
                #构建插入Mongo数据库的字典data
                data = {
                '日期': weather.get('date'),
                '星期': weather.get('wk'),
                '最高温度':weather.get('hmax'),
                '最低温度':weather.get('hmin'),
                '降水概率':weather.get('hgl')
                }
                self.jilin_weather.insert_one(data)
    if __name__ == '__main__':
        jl_weather = WeatherSpider()
        jl_weather.create_url()
    

    实现效果图:


    存入Mongo数据库.png

    (8)程序代码3(存储到CSV文件)

    import requests
    import json
    import csv
    class WeatherSpider(object):
        #csv文件表头
        with open('jilin_weather.csv', 'w') as f:
            f_csv = csv.writer(f)
            f_csv.writerow(['日期', '星期', '最高温', '最低温', '降水概率'])
        def __inti__(self):
            pass
        def request(self,url):
            #请求头(不带Referer将返回403,用Postman测试)
            headers = {
            'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36',
            'Referer': 'http://www.weather.com.cn/weather40d/101060201.shtml'
            }
            return requests.get(url,headers=headers)
        def create_url(self):
            year = '2016'
            for i in range(1,13):
                month = str(i) if i > 9 else "0" + str(i) #给一位数前加0
                url = "http://d1.weather.com.cn/calendar_new/" + year + "/101060201_" + year + month + ".html"
                self.get_data(url)
        def get_data(self,url):
            respone = self.request(url).content
            json_str = respone.decode(encoding='utf-8')[11:]
            weathers = json.loads(json_str)
            for weather in weathers:
                #构建插入csv文件的列表data
                data = [weather.get('date'),weather.get('wk'),weather.get('hmax'),weather.get('hmin'),weather.get('hgl')]
                with open('jilin_weather.csv', 'a') as f:   #以a(append)的方式追加写入
                    f_csv = csv.writer(f)
                    f_csv.writerow(data)
    if __name__ == '__main__':
        jl_weather = WeatherSpider()
    

    实现效果图:


    保存到CSV文件.png

    这三种数据的存储方式,代码分别引用了Python的pymysql库、pymongo库和csv库
    1.使用MySQL数据库需要提前建立数据表,并设定好对应存储数据的字段,字段的类型(int、varchat、date......)以及字段的长度。
    2.Mongo数据库我也是刚刚使用,但是对这个非关系型数据库比较有好感,因为使用它不必向MySQL数据库那样,要建立数据表和设定字段,给我的感觉就是直接将Python字典型数据直接“怼”进去既可以,比较方便。
    3.将数据保存到csv文件的方式比较简单,比较适合没有搭建数据库环境和没有数据库基础的使用者,这种类似Excel表格的文件格式,在获取数据后可以转换为Excel文件,利用VBA和Excel函数进行数据的处理。

    以上仅是个人近阶段学习的总结,可能存在着许多片面和理解不到位的地方,还请大家不吝赐教,批评指正。

    相关文章

      网友评论

      本文标题:Python 爬取天气网及3种数据储存方式(MySQL / Mo

      本文链接:https://www.haomeiwen.com/subject/npgvfxtx.html