天天看點

Python爬蟲實戰:糗事百科

      前面我們已經說了那麼多基礎知識了,下面我們做個實戰項目來挑戰一下吧。這次就用前面學的urllib和正規表達式來做,Python爬蟲爬取糗事百科的小段子。

爬取前我們先看一下我們的目标:

1.抓取糗事百科熱門段子

2.過濾帶有圖檔的段子

3.段子的釋出人,段子内容,好笑數,評論數

1.确定URL并抓取頁面代碼

首先我們确定好頁面的URL,糗事百科的網址是:http://www.qiushibaike.com,但是這個URL不友善我們後面連續抓取,我們可以看一下第二頁就知道URL如何構造了,URL是 http://www.qiushibaike.com/8hr/page/1/?s=4872200,其中中間的數字1代表頁數,我們可以傳入不同的值來獲得某一頁的段子内容,其他的部分是不變的。

我們先看看最基本的頁面抓取方式,看看會不會成功

import urllib2
page=1
url = 'http://www.qiushibaike.com/8hr/page/'+str(page)+'/?s=4872200'
try:
    request = urllib2.Request(url)
    response = urllib2.urlopen(request)
    print response.read()
except urllib2.URLError, e:
    if hasattr(e,"code"):
        print e.code
    if hasattr(e,"reason"):
        print e.reason
           

結果出現 raise BadStatusLine(line)  httplib.BadStatusLine: '',我們需要加上headers驗證,如下:

import urllib2

page=1
url = 'http://www.qiushibaike.com/8hr/page/'+str(page)+'/?s=4872200'
user_agent ='Mozilla/4.0(compatible;MSIE 5.5;Windows NT)'
headers={'User-Agent':user_agent}
try:
    request = urllib2.Request(url,headers = headers)
    response = urllib2.urlopen(request)
    print response.read()
except urllib2.URLError, e:
    if hasattr(e,"code"):
        print e.code
    if hasattr(e,"reason"):
        print e.reason
           

好啦,運作正常,頁面代碼也列印出來了。

2、用正規表達式提取段子

我們先看審查元素,看一下代碼,如下圖:

Python爬蟲實戰:糗事百科

每個段子都在一個盒子裡,<div class="article block untagged mb15" id="qiushi_tag_116124511"><div class="author clearfix">...</div> 現在我們需要 段子的釋出人,段子内容,好笑數,評論數,用正規表達式比對如下:

content = response.read().decode('utf-8')
    pattern = re.compile('<div.*?author clearfix">.*?<a.*?<img.*?>.*?</a>.*?<a.*?>.*?<h2>(.*?)</h2>.*?content">'+
                         '(.*?)</div>.*?<div class="stats">.*?vote".*?number">(.*?)</i>.*?stats-comments".*?<a.*?number">(.*?)</i>',re.S)
    items = re.findall(pattern,content)
    for item in items :
            print item[0],item[1],item[2],item[3]
           

看一下爬出來的段子:

Python爬蟲實戰:糗事百科

好啦下面我們把代碼完整的留下,加了一個小循環,爬取10頁:

# _*_ coding:utf-8 _*_

import urllib2
import re


page=1
print u"第%d頁"%page
while page < 10:
    url = 'http://www.qiushibaike.com/8hr/page/' + str(page) + '/?s=4872200'
    user_agent ='Mozilla/4.0(compatible;MSIE 5.5;Windows NT)'
    headers={'User-Agent':user_agent}
    try:
        request = urllib2.Request(url,headers = headers)
        response = urllib2.urlopen(request)
        content = response.read().decode('utf-8')
        pattern = re.compile('<div.*?author clearfix">.*?<a.*?<img.*?>.*?</a>.*?<a.*?>.*?<h2>(.*?)</h2>.*?content">' +
                             '(.*?)</div>.*?<div class="stats">.*?vote".*?number">(.*?)</i>.*?stats-comments".*?<a.*?number">(.*?)</i>',re.S)
        items = re.findall(pattern,content)
        for item in items :
                print item[0],item[1],item[2],item[3]

    except urllib2.URLError, e:
        if hasattr(e,"code"):
            print e.code
        if hasattr(e,"reason"):
            print e.reason

    page = page + 1
    print u"第%d頁"%page
           

好啦,代碼比較糙,大家可以自己試試!