Python爬蟲----抓取豆瓣電影Top250

有了上次利用python爬蟲抓取糗事百科的經驗,此次本身動手寫了個爬蟲抓取豆瓣電影Top250的簡要信息。html

1.觀察urlpython

首先觀察一下網址的結構 http://movie.douban.com/top250?start=0&filter=&type= :正則表達式

能夠看到,問號?後有三個參數 start、filter、type,其中start表明頁碼,每頁展現25部電影,0表明第一頁,以此類推25表明第二頁,50表明第三頁...設計模式

filter顧名思義,是過濾已經看過的電影,filter和type在這裏不重要,能夠無論。app

2.查看網頁源代碼python爬蟲

打開上面的網址,查看源代碼,能夠看到信息的展現結構以下:ide

 1 <ol class="grid_view">
 2         <li>
 3             <div class="item">
 4                 <div class="pic">
 5                     <em class="">1</em>
 6                     <a href="http://movie.douban.com/subject/1292052/">
 7                         <img alt="肖申克的救贖" src="http://img3.douban.com/view/movie_poster_cover/ipst/public/p480747492.jpg" class="">
 8                     </a>
 9                 </div>
10                 <div class="info">
11                     <div class="hd">
12                         <a href="http://movie.douban.com/subject/1292052/" class="">
13                             <span class="title">肖申克的救贖</span>
14                                     <span class="title">&nbsp;/&nbsp;The Shawshank Redemption</span>
15                                 <span class="other">&nbsp;/&nbsp;月黑高飛(港)  /  刺激1995(臺)</span>
16                         </a>
17 
18 
19                             <span class="playable">[可播放]</span>
20                     </div>
21                     <div class="bd">
22                         <p class="">
23                             導演: 弗蘭克·德拉邦特 Frank Darabont&nbsp;&nbsp;&nbsp;主演: 蒂姆·羅賓斯 Tim Robbins /...<br>
24                             1994&nbsp;/&nbsp;美國&nbsp;/&nbsp;犯罪 劇情
25                         </p>
26 
27                         
28                         <div class="star">
29                                 <span class="rating5-t"><em>9.6</em></span>
30                                 &nbsp;<span>646374人評價</span>
31                         </div>
32 
33                             <p class="quote">
34                                 <span class="inq">但願讓人自由。</span>
35                             </p>
36                     </div>
37                 </div>
38             </div>
39         </li>

其中<em class="">1</em>表明排名,<span class="title">肖申克的救贖</span>表明電影名,其餘信息的含義也很容易能看出來。post

因而接下來能夠寫正則表達式:編碼

 1 pattern = re.compile(u'<div.*?class="item">.*?<div.*?class="pic">.*?'
 2                              + u'<em.*?class="">(.*?)</em>.*?'
 3                              + u'<div.*?class="info">.*?<span.*?class="title">(.*?)'
 4                              + u'</span>.*?<span.*?class="title">(.*?)</span>.*?'
 5                              + u'<span.*?class="other">(.*?)</span>.*?</a>.*?'
 6                              + u'<div.*?class="bd">.*?<p.*?class="">.*?'
 7                              + u'導演: (.*?)&nbsp;&nbsp;&nbsp;'
 8                              + u'主演: (.*?)<br>'
 9                              + u'(.*?)&nbsp;/&nbsp;(.*?)&nbsp;/&nbsp;'
10                              + u'(.*?)</p>'
11                              + u'.*?<div.*?class="star">.*?<em>(.*?)</em>'
12                              + u'.*?<span>(.*?)人評價</span>.*?<p.*?class="quote">.*?'
13                              + u'<span.*?class="inq">(.*?)</span>.*?</p>', re.S)

在此處flag參數re.S表明多行匹配。url

3.使用面向對象的設計模式編碼

代碼以下:

 1 # -*- coding:utf-8 -*-
 2 __author__ = 'Jz'
 3 import urllib2
 4 import re
 5 import sys
 6 
 7 class MovieTop250:
 8     def __init__(self):
 9         #設置默認編碼格式爲utf-8
10         reload(sys)
11         sys.setdefaultencoding('utf-8')
12         self.start = 0
13         self.param = '&filter=&type='
14         self.headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64)'}
15         self.movieList = []
16         self.filePath = 'D:/coding_file/python_file/File/DoubanTop250.txt'
17     
18     def getPage(self):
19         try:
20             URL = 'http://movie.douban.com/top250?start=' + str(self.start)
21             request = urllib2.Request(url = URL, headers = self.headers)
22             response = urllib2.urlopen(request)
23             page = response.read().decode('utf-8')
24             pageNum = (self.start + 25)/25
25             print '正在抓取第' + str(pageNum) + '頁數據...' 
26             self.start += 25
27             return page
28         except urllib2.URLError, e:
29             if hasattr(e, 'reason'):
30                 print '抓取失敗,具體緣由:', e.reason
31     
32     def getMovie(self):
33         pattern = re.compile(u'<div.*?class="item">.*?<div.*?class="pic">.*?'
34                              + u'<em.*?class="">(.*?)</em>.*?'
35                              + u'<div.*?class="info">.*?<span.*?class="title">(.*?)'
36                              + u'</span>.*?<span.*?class="title">(.*?)</span>.*?'
37                              + u'<span.*?class="other">(.*?)</span>.*?</a>.*?'
38                              + u'<div.*?class="bd">.*?<p.*?class="">.*?'
39                              + u'導演: (.*?)&nbsp;&nbsp;&nbsp;'
40                              + u'主演: (.*?)<br>'
41                              + u'(.*?)&nbsp;/&nbsp;(.*?)&nbsp;/&nbsp;'
42                              + u'(.*?)</p>'
43                              + u'.*?<div.*?class="star">.*?<em>(.*?)</em>'
44                              + u'.*?<span>(.*?)人評價</span>.*?<p.*?class="quote">.*?'
45                              + u'<span.*?class="inq">(.*?)</span>.*?</p>', re.S)
46         while self.start <= 225:
47             page = self.getPage()
48             movies = re.findall(pattern, page)
49             for movie in movies:
50                 self.movieList.append([movie[0], movie[1], movie[2].lstrip('&nbsp;/&nbsp;'), 
51                       movie[3].lstrip('&nbsp;/&nbsp;'), movie[4], 
52                       movie[5], movie[6].lstrip(), movie[7], movie[8].rstrip(),
53                       movie[9], movie[10], movie[11]])
54     
55     def writeTxt(self):
56         fileTop250 = open(self.filePath, 'w')
57         try:
58             for movie in self.movieList:
59                 fileTop250.write('電影排名:' + movie[0] + '\r\n')
60                 fileTop250.write('電影名稱:' + movie[1] + '\r\n')
61                 fileTop250.write('外文名稱:' + movie[2] + '\r\n')
62                 fileTop250.write('電影別名:' + movie[3] + '\r\n')
63                 fileTop250.write('導演姓名:' + movie[4] + '\r\n')
64                 fileTop250.write('參與主演:' + movie[5] + '\r\n')
65                 fileTop250.write('上映年份:' + movie[6] + '\r\n')
66                 fileTop250.write('製做國家/地區:' + movie[7] + '\r\n')
67                 fileTop250.write('電影類別:' + movie[8] + '\r\n')
68                 fileTop250.write('電影評分:' + movie[9] + '\r\n')
69                 fileTop250.write('參評人數:' + movie[10] + '\r\n')
70                 fileTop250.write('簡短影評:' + movie[11] + '\r\n\r\n')
71             print '文件寫入成功...'
72         finally:
73             fileTop250.close()
74     
75     def main(self):
76         print '正在從豆瓣電影Top250抓取數據...'
77         self.getMovie()
78         self.writeTxt()
79         print '抓取完畢...'
80 
81 DouBanSpider = MovieTop250()
82 DouBanSpider.main()

代碼比較簡單,最後將信息寫入一個文件,沒有什麼須要解釋的地方。

4.運行截圖

5.問題說明

打開文件瀏覽時發現有個別電影沒有抓取下來或者信息中出現html代碼,後來排查發現是由於豆瓣有部分電影的信息不全,缺乏主演等致使html代碼出現差別而致使正則表達式沒有匹配到或者匹配出錯。

相關文章
相關標籤/搜索
本站公眾號
   歡迎關注本站公眾號,獲取更多信息