Python爬蟲天氣預報執行個體詳解(小白入門),python爬蟲

來源:互聯網
上載者:User

Python爬蟲天氣預報執行個體詳解(小白入門),python爬蟲

本文研究的主要是Python爬蟲天氣預報的相關內容,具體介紹如下。

這次要爬的網站是這個:http://www.weather.com.cn/forecast/

要求是把你所在城市過去一年的曆史資料爬出來。

分析網站

首先來到目標資料的網頁 http://www.weather.com.cn/weather40d/101280701.shtml

我們可以看到,我們需要的天氣資料都是放在圖表上的,在切換月份的時候,發現只有部分頁面重新整理了,就是天氣資料的那塊,而URL沒有變化。

這是因為網頁前端使用了JS非同步載入的技術,更新時不用載入整個頁面,從而提升了網頁的載入速度。

對於這種非靜態頁面,我們在請求資料時,就不能簡單的通過替換URL來請求不同的頁面。

著眼點要放在Network,觀察整個請求的過程,從中尋找突破口。

老規矩按下F12 > network,切換下頁面,發現多了一些東西,這就是切換月份,瀏覽器發出的請求,可以很清楚的看到要求標頭和請求參數。

再來看看Response是怎樣的吧

真是沒想到,返回的居然是json格式的天氣資料!直接做 json 反序化就能變成字典的形式,省掉了我們解析 html 的麻煩呀。既然找到了資料所在的地方,就可以開始嘗試構建請求了。

構建請求

先直接copy上面的Request URL,試下請求。http://d1.weather.com.cn/calendar_new/2017/101280701_201706.html?_=1495720234075
然後發現報錯了,先把要求標頭全部滿上懟進去,發現可以正常的響應。
但是我們還要分析下到底哪個參數不對出了問題。經過嘗試,發現要求標頭裡的Referer的原因,去掉就會報錯。

這是因為這是瀏覽器發出請求時,會通過Referer告訴伺服器我是從哪個頁面連結過來的,有些網站會對這個做驗證,主要時為了防止別人盜鏈的問題。

這個中國天氣網,就是驗證了Referer裡的網域名稱是不是自己的,不是的話就會403禁止訪問伺服器。

接下來就要考慮怎麼請求不同月份的資料。

通過觀察URL,發現其實很簡單,直接替換年月,就可以迴圈抓取,得到整年的資料。

那中間的101280701是什麼意思呢,經過請求不同的城市對比URL,我發現這是表示地理位置的一個資料。

前3位表示國家中國,後6位依次表示,省份,城市和區縣。修改這裡,就能實現對不同城市進行查詢了。

最後一個參數1495720234075,開始以為是隨機數,後來有朋友提醒這是unix時間戳記,實際上就算去掉這個,也能正常訪問資料,沒什麼影響。

解析資料

拿到資料以後,就可以開始解析了。不過這雷根本用不上xpath,直接用Json.load(),就能還原序列化成json對象,從中取出字典,節省很多麻煩。需要注意的是,返回的40天的天氣資料 fc40 字串是這樣

var fc40 = [{"blue":"","c1":"","c2":"","cla":"history","date":"20151227","des":"曆史均值","fe":"","hgl":"17%","hmax":"17","hmin":"13","hol":"","jq":""
.....]}

前面的字串需要去掉,才能還原序列化,注意這裡的json對象實際是個儲存字典的list[]。開始想用正則,不過不熟沒弄好。後來發現 python 字串也能使用這樣的文法 [a:b] 來取出位置a到位置b的字串,所以就直接用[11 : ], 就能取出fc40 後面的字串,也很方便。

儲存資料

因為資料量比較大,就採用mongodb來做資料持久化。mongodb 我也是才學習,參考了別人的教程,才做好了環境配置,過程打算總結到另一篇,這裡就打算不多說了。

因為原本的放了天氣資料的字典裡面有太多沒用的資料,我只想提取出我想要的部分,就用了一個小技巧。

將想要的資料的key,儲存成subkey這個字典,用 for in取出subkey中的key,再回到原本的dict中取出對應的值,最後將這些索引值對,都儲存在一個subdict字典裡,就完成了提取出子字典的功能。說起來很麻煩,但是代碼卻很簡單,這可能就是python的魅力吧。

subkey = {'date', 'hmax', 'hmin', 'hgl', 'fe', 'wk', 'time'}subdict = {key: dict[key] for key in subkey}

然後我還做了個用中文替換的原來key的功能,只需要稍作修改,for in 取出來的是索引值對,然後用中文的value,替換英文的key,就ok了。

 subkey = {'date': '日期', 'hmax': '最高溫度', 'hmin': '最低溫度', 'hgl': '降水機率', 'fe': '節日', 'wk': '星期'} subdict = {value: dict[key] for key, value in subkey.items()}

最後的結果如,這是用pycharm上的mongodb可視化外掛程式Mongo Plugin看到的,在pycharm>settings>plugins裡面可以搜尋安裝。需要注意的是,預設只顯示300條資料。想要看到更多,就在Row limit 上輸入總數就行。

Python的代碼非常短才30多行,就完成了爬蟲的整個流程, 請求,解析,儲存,一氣呵成,可謂是爬蟲界的豪傑。

# encoding=utf-8import requestsimport jsonimport pymongoimport timedef request(year, month):  url = "http://d1.weather.com.cn/calendar_new/" + year + "/101280701_" + year + month + ".html?_=1495685758174"  headers = {    "User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.102 Safari/537.36",    "Referer": "http://www.weather.com.cn/weather40d/101280701.shtml",  }  return requests.get(url, headers=headers)def parse(res):  json_str = res.content.decode(encoding='utf-8')[11:]  return json.loads(json_str)def save(list):  subkey = {'date': '日期', 'hmax': '最高溫度', 'hmin': '最低溫度', 'hgl': '降水機率', 'fe': '節日', 'wk': '星期', 'time': '發布時間'}  for dict in list:    subdict = {value: dict[key] for key, value in subkey.items()}  #提取原字典中部分索引值對,並替換key為中文    forecast.insert_one(subdict)                  #插入mongodb資料庫if __name__ == '__main__':  year = "2016"  month = 1  client = pymongo.MongoClient('localhost', 27017)  # 串連mongodb,連接埠27017  test = client['test']               # 建立資料庫檔案test  forecast = test['forecast']            # 建立表forecast  for i in range(month, 13):    month = str(i) if i > 9 else "0" + str(i)   #小於10的月份要補0    save(parse(request(year, month)))       

time.sleep(1)

總結

以上就是本文關於Python爬蟲天氣預報執行個體詳解(小白入門)的全部內容,希望對大家有所協助。感興趣的朋友可以繼續參閱本站其他相關專題,如有不足之處,歡迎留言指出。感謝朋友們對本站的支援!

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.