Python爬虫零基础实例---爬取小说吧小说内容到本地

Python爬虫实例--爬取百度贴吧小说

写在前面

本篇文章是我在简书上写的第一篇技术文章,作为一个理科生,能把仅剩的一点文笔拿出来献丑已是不易,希望大家能在指教我的同时给予我一点点鼓励,谢谢。


一.介绍

小说吧:顾名思义,是一个小说爱好者的一个聚集地。当然这不是重点,重点是,我们要做的事情便是将小说吧中以帖子连载形式的小说用爬虫给拿下来保存到本地

这个项目是我曾初学python之时做的一个练习项目,现在再重新拿出来作为一篇开篇简作献给大家。阅读本文不需要有很高的python技术或者爬虫知识,只要略微有些python基础就可以,在一些地方,我会尽量给大家详细备注。

二.环境

Python版本:Python2.7

IDE:Pycharm2017

第三方库:
urllib2 模块:urllib2是python的一个获取url(Uniform ResourceLocators,统一资源定址器)的模块。
re模块:Python 的 re模块(Regular Expression 正则表达式)提供各种正则表达式的匹配操作

注:以上两个第三方库在Python2.7中自带,因此不用再安装。本案例在使用第三方库函数时会详细介绍用法与功能。

三.案例

1.导入模块

首先创建一个python文件,我这里为main.py(文件名随意取,本案例只使用一个py文件)。本案例中我们使用两个模块urllib2re,因此首先导入模块.

# -*- coding:utf-8 -*-
import urllib2 , re

当然,python2版本需要在开头声明编码格式。除了上述代码的写法以外,也可以这样声明

# coding = utf-8

2.理解思路

我个人在做项目前习惯先分析项目,将步骤一步一步的写出来,然后去慢慢实现。

  1. 找到目标网页,获取源码
  2. 匹配标题,获取标题内容
  3. 匹配正文,获取正文内容
  4. 去除或者替换杂项

OK,这里思路就是这样的一个四部曲。现在来看一下代码框架。

# -*- coding:utf-8 -*-
import urllib2 , re


#这是本案例的类
class Novel:

    baseUrl = '' #这里是你要爬取的小说的链接
    #这个方法用来获取网页源码
    def getPage(self):
        pass
    #这个方法用来获取小说标题并保存
    def getTitle(self):
        pass
    #这个方法用来获取小说文本并保存
    def getText(self):
        pass

#这是一个测试模块,执行本文件时的入口
if __name__ == '__main__':
    n = Novel() #实例化一个类
    #print n.getPage() #获取网页源码
    n.getTitle()#获取小说题目
    n.getText() #获取小说内容

现在开始一步步实现功能:

1.找到目标网页,获取网页源码

我在小说吧精品贴里面随便翻了一个帖子,就以这个帖子为案例。
【原创】《贫僧为什么不可以谈恋爱》(古言,长篇)
现在我们需要爬取这个帖子中小说内容,我们需要直接将它的链接地址给baseUrl吗?当然不是
爬取一个帖子上的小说,实际上是去爬取该小说作者的所发表的内容,所以我们还需要进行一步操作,只看楼主

这里写图片描述

我们所需要的链接地址,就是当前这个了

https://tieba.baidu.com/p/4973334088?see_lz=1
注意一定是要只看楼主后的链接,比之前的会多出个?see_lz=1

现在就将你得到的链接地址赋值给baseUrl

baseUrl = 'https://tieba.baidu.com/p/4973334088?see_lz=1'

接下来我们来获取这个网页的源码,也就是实现getPage函数:

    def getPage(self):
        request = urllib2.Request(self.baseUrl)
        response = urllib2.urlopen(request).read()
        return response

本函数现实通过以基本链接baseUrl为参数实现了一个Request请求类的对象request。接着通过urlopen去执行request请求对象打开目标网页。接着通过调用read`函数获取目标网页的源码,并作为函数返回值返回.
返回的网页源码,可在测试代码块中通过调用输出本函数查看。
例:

if __name__ == '__main__':
    n = Novel() #实例化一个类
    print n.getPage() #获取网页源码

2.匹配标题,获取标题内容

首先先亮出我的代码:

    def getTitle(self):
        html = self.getPage() #调用获取源码
        #r防止转义
        reg = re.compile(r'<h3 class="core_title_txt pull-left text-overflow  " title="(.*?)" style=')
        items = re.findall(reg,html)
        for item in items:
            print item
            f = open('novel.txt','w')
            f.write('标题===>>>'+item)
            f.close()

注意:代码错行要在行末加\
例如:

print 'hello   \
          world'

首先我们在网页源码中寻找包含小说主题部分的源码,可以通过Ctrl+F搜索。查找到<div>^=……中间包含小说主题<.div>这么一长串的包含小说主题的代码。只要将主题部分全部置换为(.*?)号就可以了。

在正则表达式中的含义:
.:匹配任意字符,除了换行符
:匹配前面的子表达式零次或多次
?:匹配前面的子表达式零次或一次
():标记一个子表达式的开始和结束位置。子表达式可以获取供以后使用
(.>)
:匹配所有满足条件的表达式并作为结果集返回

re.compile函数是将正则表达式的字符串形式编译为Pattern实例,然后使用Pattern实例处理文本并获得匹配结果,其中字符串前的r是为了防止转义
findall(正则表达式,文本) ------将满足的匹配结果以list列表返回
用迭代拿到items中的主题名后在将之写入名为novel.txt的文件中

3.匹配正文,获取小说正文内容

匹配正文,与匹配标题相差无几,首先是寻找以楼主发表的第一层为例的代码<div>段,从中获取可以作为正则匹配的语句。并将正文部分改为(.*?)
如下

class="d_post_content j_d_post_content "> (.*?)</div><br>
实现函数如下:

    #这个方法用来获取小说文本并保存
    def getText(self):
        html = self.getPage()
        reg = re.compile(r'class="d_post_content j_d_post_content ">            (.*?)</div><br>',re.S)#匹配换行符
        req = re.findall(reg,html)
        for i in req:
            print i
            f = open('novel.txt','a') #a 追加模式
            f.write('\n'+i)
            f.close()

如同匹配主题一样的步骤匹配正文,但是并没有结束,因为你会在你的结果中看到这样


杂乱无章

对没错。杂乱无章的正文,中间还有HTML中的<a>,<img>,<br>等标签
我们接着来处理

4.替换或者去出杂项

re模块中有sub函数

sub(被替换的内容,替换的内容,需要处理的文本) ---- 返回处理后的文本

现在我们将杂项全部给替换成空字符吧""
当然<br>标签可以直接调用字符串中的replace函数替换成换行符\n

修改后的函数模块如下:

    def getText(self):
        html = self.getPage()
        reg = re.compile(r'class="d_post_content j_d_post_content ">            (.*?)</div><br>',re.S)#匹配换行符
        req = re.findall(reg,html)
        for i in req:
            removeA = re.compile('<a.*?>|</a>')
            removeIMG = re.compile('<img.*?>')
            removeHTTP = re.compile('<http.*?.html>')
            i = re.sub(removeA,"",i)
            i = re.sub(removeIMG,"",i)
            i = re.sub(removeHTTP,"",i)
            i = i.replace('<br>','\n')
            print i
            f = open('novel.txt','a') #a 追加模式
            f.write('\n'+i)
            f.close()

注意:记得在打开文件函数中,对文件的操作方式为a追加模式

案例结束:
将完整代码贴给大家:

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

import urllib2 , re

#这是本案例的类
class Novel:
    baseUrl = 'https://tieba.baidu.com/p/4973334088?see_lz=1' #这里是你要爬取的小说的链接
    #这个方法用来获取网页源码
    def getPage(self):
        request = urllib2.Request(self.baseUrl) 
        response = urllib2.urlopen(request).read()
        return response
    #这个方法用来获取小说标题并保存
    def getTitle(self):
        html = self.getPage() #调用获取源码
        #r防止转义
        reg = re.compile(r'<h3 class="core_title_txt pull-left text-overflow  " title="(.*?)" style=')
        items = re.findall(reg,html)
        for item in items:
            print item
            f = open('novel.txt','w')
            f.write('标题===>>>'+item)
            f.close()

    #这个方法用来获取小说文本并保存
    def getText(self):
        html = self.getPage()
        reg = re.compile(r'class="d_post_content j_d_post_content ">            (.*?)</div><br>',re.S)#匹配换行符
        req = re.findall(reg,html)
        for i in req:
            removeA = re.compile('<a.*?>|</a>')
            removeIMG = re.compile('<img.*?>')
            removeHTTP = re.compile('<http.*?.html>')
            i = re.sub(removeA,"",i)
            i = re.sub(removeIMG,"",i)
            i = re.sub(removeHTTP,"",i)
            i = i.replace('<br>','\n')
            print i
            f = open('novel.txt','a') #a 追加模式
            f.write('\n'+i)
            f.close()
#这是一个测试代码块,执行本文件时的入口
if __name__ == '__main__':
    n = Novel() #实例化一个类
    #print n.getPage() #获取网页源码
    n.getTitle()#获取小说题目
    n.getText() #获取小说内容

以后想要获取小说吧哪个小说,只要将baseUrl的地址修改一下就好咯。




撒花撒花撒花,从11点写到了将近2点,终于搞定了。
因为是第一次写技术文写这么长时间,所以,,后面耐心不太好,导致后半篇文章质量太差劲。
不过,终究是先搞完了一篇哪,简书处女技术作。。
至于文章瑕疵,我在白天会花时间去修改,也希望大家给我多多提意见。我呢~争取展现给大家的是一篇更加完美的文章。

夜了,晚安。


看在作者君这么辛苦的份上,求您点个喜欢吧!!

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 160,333评论 4 364
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,812评论 1 298
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 110,016评论 0 246
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,293评论 0 214
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,650评论 3 288
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,788评论 1 222
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 32,003评论 2 315
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,741评论 0 204
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,462评论 1 246
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,681评论 2 249
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,168评论 1 262
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,528评论 3 258
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,169评论 3 238
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,119评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,902评论 0 198
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,846评论 2 283
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,719评论 2 274

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 170,580评论 25 707
  • # Python 资源大全中文版 我想很多程序员应该记得 GitHub 上有一个 Awesome - XXX 系列...
    aimaile阅读 26,301评论 6 428
  • 那一院静默的僧人 在我眼中是一本平装的故事书 每件青衣之下 都曾是深邃而遥远的故事 走出庙门 我看见滚滚红尘 那是...
    徐曙光阅读 251评论 0 2
  • 各位爸爸妈妈们,大家好! 先表扬孩子们今天的表现,今天孩子们全都带了红领巾了,这真是开学以来第一回啊,值得表扬,说...
    阳光温温阅读 270评论 2 4
  • 原文链接:http://wyb0.com/posts/docker-image-and-container 操作系...
    cws阅读 723评论 0 0