写了一个之前没完成的项目,代码优化不够,速度有点慢,应该也有错误的地方,望大佬看了之后能给点建议。。。。。。。。。

这是开始的url,先看一下它的网页结构:http://www.cymodel.net/deaafc/13143.html,可以观察到,整个网页大致分为六部分内容,中间的正文部分,右边的四部分新闻板块,还有最下面的一部分社会新闻。而每一个新闻链接点进去后又是一个相同模样的页面,爬取的目标是获取到所有的新闻title和对应的url。下面是代码,每部分链接的提取都差不多,利用find_all返回结果列表,然后再对列表进行遍历。

 import requests
from bs4 import BeautifulSoup # response请求页面的响应,all_url_lis用于存放所有页面的utl,all_title_list用于存放所有页面的title,
# i用来显示当前爬取到第几个页面 def parse(response, all_url_list, all_title_list, i):
html = response.content # 先获取二进制形式的内容,下面再进行转换,否则会出现中文乱码
html = str(html, encoding='utf-8')
soup = BeautifulSoup(html, 'lxml') # 利用Beautifulsoup解析库
f = open('title_and_url.txt', 'a', encoding='utf-8') # 打开文件,存储所有页面的title和url # 获取正文
# content = soup.find(name='div', attrs={'class': 'main_article'})
# p_list = content.find_all(name='p')
# for p in p_list:
# print(p.string) flag = 0 # 用来标志当前页面的url有多少已经存储过了,后面可以作为结束循环的条件 # 获取下方社会新闻
Sociology_list = soup.find_all(name='div', attrs={'class': 'r'})
sociology_a_list = Sociology_list[0].find_all(name='a')
for a in sociology_a_list:
sociology_title = a.string
sociology_url = a.attrs.get('href')
# print(sociology_title, sociology_url)
# 判断列表中是否已经存在这个页面的url或title,实现去重
if sociology_url not in all_url_list and sociology_title not in all_title_list:
all_url_list.append(sociology_url)
all_title_list.append(sociology_title)
f.write(sociology_title + ' ' + sociology_url + '\n')
else:
flag += 1 # 获取排行榜
Ranking_list = soup.find_all(name='ul', attrs={'class': 'tt', 'id': 'tt'})
rank_a_list = Ranking_list[0].find_all(name='a')
for a in rank_a_list:
rank_title = a.string
rank_url = a.attrs.get('href')
# print(rank_title, rank_url)
if rank_url not in all_url_list and rank_title not in all_title_list:
all_url_list.append(rank_url)
all_title_list.append(rank_title)
f.write(rank_title + ' ' + rank_url + '\n')
else:
flag += 1 # 热点推荐
hot_list = soup.find_all(name='ul', attrs={'class': 'ducheng_list'})
hot_a_list = hot_list[0].find_all(name='a')
for a in hot_a_list:
hot_title = a.string
hot_url = a.attrs.get('href')
# print(hot_title, hot_url)
if hot_url not in all_url_list and hot_title not in all_title_list:
all_url_list.append(hot_url)
all_title_list.append(hot_title)
f.write(hot_title + ' ' + hot_url + '\n')
else:
flag += 1 # 热点视频
video_list = soup.find_all(name='ul', attrs={'class': 'tuku_list'})
video_a_list = video_list[0].find_all(name='a')
for a in video_a_list:
video_title = a.string
video_url = a.attrs.get('href')
# print(video_title, video_url)
if video_url not in all_url_list and video_title not in all_title_list:
all_url_list.append(video_url)
all_title_list.append(video_title)
f.write(video_title + ' ' + video_url + '\n')
else:
flag += 1 # 要闻
yaowen_list = soup.find_all(name='ul', attrs={'class': 'yaowen_list'})
yaowen_a_list = yaowen_list[0].find_all(name='a')
for a in yaowen_a_list:
yaowen_title = a.string
yaowen_url = a.attrs.get('href')
# print(yaowen_title, yaowen_url)
if yaowen_url not in all_url_list and yaowen_title not in all_title_list:
all_url_list.append(yaowen_url)
all_title_list.append(yaowen_title)
f.write(yaowen_title + ' ' + yaowen_url + '\n')
else:
flag += 1 f.close()
print('第{0}个页面存储完成'.format(i), flag)
# 一个页面中有44条新闻。如果改页面中的所有url都已经被存储过了,则可以大致认为已经获取到了所有的url
# 实际少了十三条
if flag == 44:
return flag
else:
return if __name__ == '__main__':
all_url_list = []
all_title_list = []
url = 'http://www.cymodel.net/deaafc/13143.html'
all_url_list.append(url)
i = 0
while (True):
# 如果想要把all_url_list里面的每个页面的url全部爬取一遍,则可以用这个条件作为循环结束
# 把下面的内嵌if和函数里面的if else注释掉即可
if( i < len(all_url_list) ):
response = requests.get(url=all_url_list[i])
flag = parse(response, all_url_list, all_title_list, i+1)
i += 1
if flag == 44:
print('已爬取大部分的url!!!!!')
break
else:
print('已爬取到所有的url!!!!!')
break

再写的时候,主要遇到了两个问题,一是如何实现去重,二是爬取到什么时候结束。

第一个问题的解决办法是,先定义两个列表,用于存放每个页面的url和title,也就是all_url_liat和all_title_list,然后再每次存放url和title之前,先判断列表里面有没有这个url,如果没有,则进行存储,并添加到列表中。本来之定义了一个url的列表,但后来发现有的网页之间url不同,title相同,里面的内容也相同,所以又加了一个all_title_list。用这种方法实现去重的好处是比较简单,容易想到,但坏处是列表里面的元素过多,比较占内容,会有两个具有四百多个元素的列表,而且每次添加数据前,都要过一遍列表,判断要添加的url是否已经再列表中,这样就会导致程序运行较慢。

第二个问题的解决办法一是根据每个页面未被存储的url数量判断,每个页面中共有44个新闻的链接,如果改页面中的44个链接都已经被存储过了,那么就认为已经获取到了大部分的url,第二种办法是把all_url_list中的每个url都爬取一下,这样能获取到所有的新闻链接,但耗时有点长,代码还需要优化。第一种办法的获取结果为416条,第二种办法获取到的是429条。

*****************************不积跬步,无以至千里。 *****************************

python爬虫之深度爬取实例的更多相关文章

  1. Python爬虫教程-17-ajax爬取实例(豆瓣电影)

    Python爬虫教程-17-ajax爬取实例(豆瓣电影) ajax: 简单的说,就是一段js代码,通过这段代码,可以让页面发送异步的请求,或者向服务器发送一个东西,即和服务器进行交互 对于ajax: ...

  2. 【转载】教你分分钟学会用python爬虫框架Scrapy爬取心目中的女神

    原文:教你分分钟学会用python爬虫框架Scrapy爬取心目中的女神 本博文将带领你从入门到精通爬虫框架Scrapy,最终具备爬取任何网页的数据的能力.本文以校花网为例进行爬取,校花网:http:/ ...

  3. python爬虫-基础入门-爬取整个网站《3》

    python爬虫-基础入门-爬取整个网站<3> 描述: 前两章粗略的讲述了python2.python3爬取整个网站,这章节简单的记录一下python2.python3的区别 python ...

  4. python爬虫-基础入门-爬取整个网站《2》

    python爬虫-基础入门-爬取整个网站<2> 描述: 开场白已在<python爬虫-基础入门-爬取整个网站<1>>中描述过了,这里不在描述,只附上 python3 ...

  5. python爬虫-基础入门-爬取整个网站《1》

    python爬虫-基础入门-爬取整个网站<1> 描述: 使用环境:python2.7.15 ,开发工具:pycharm,现爬取一个网站页面(http://www.baidu.com)所有数 ...

  6. Python 爬虫入门之爬取妹子图

    Python 爬虫入门之爬取妹子图 来源:李英杰  链接: https://segmentfault.com/a/1190000015798452 听说你写代码没动力?本文就给你动力,爬取妹子图.如果 ...

  7. Python爬虫实战之爬取百度贴吧帖子

    大家好,上次我们实验了爬取了糗事百科的段子,那么这次我们来尝试一下爬取百度贴吧的帖子.与上一篇不同的是,这次我们需要用到文件的相关操作. 本篇目标 对百度贴吧的任意帖子进行抓取 指定是否只抓取楼主发帖 ...

  8. python 爬虫 requests+BeautifulSoup 爬取巨潮资讯公司概况代码实例

    第一次写一个算是比较完整的爬虫,自我感觉极差啊,代码low,效率差,也没有保存到本地文件或者数据库,强行使用了一波多线程导致数据顺序发生了变化... 贴在这里,引以为戒吧. # -*- coding: ...

  9. 教你分分钟学会用python爬虫框架Scrapy爬取心目中的女神

    本博文将带领你从入门到精通爬虫框架Scrapy,最终具备爬取任何网页的数据的能力.本文以校花网为例进行爬取,校花网:http://www.xiaohuar.com/,让你体验爬取校花的成就感. Scr ...

随机推荐

  1. Docker组成三要素

    目录 镜像 容器 仓库 总结 Docker的基本组成三要素 镜像 容器 仓库 镜像 Docker 镜像(Image)就是一个只读的模板.镜像可以用来创建 Docker 容器,一个镜像可以创建很多容器. ...

  2. 实操《kubernetes网络权威指南》之tun设备

    跟着网上作一次,OK的. tun.c #include <net/if.h> #include <sys/ioctl.h> #include <sys/stat.h> ...

  3. HashMap默认加载因子为什么选择0.75?(阿里)

    Hashtable 初始容量是11 ,扩容 方式为2N+1; HashMap 初始容量是16,扩容方式为2N; 阿里的人突然问我为啥扩容因子是0.75,回来总结了一下: 提高空间利用率和 减少查询成本 ...

  4. day_92_11_14flask的启动和orm,反向生成model

    一.自定义命令. 在flask中也可以将应用改写成可以使用命令的形式,需要用到模块: pip install flask-script 使用关键字manage使得其能使用终端启动: from flas ...

  5. 15.flag在index里

    查看一下源代码 点进去,发现没有什么有价值的东西~ 根据题目提示flag在index.php里面,所以我们可以通过php://filter读取文件内容 构造payload: http://123.20 ...

  6. flask之web网关、三件套、配置、路由(参数、转化器及自定义转化器)、cbv、模板语言、session

    目录 1.wsgiref.py 2.werzeug.py 3.三件套 4.配置文件 5.路由本质 6.cbv.py 7.路由转化器 8.自定义转化器 9.模板语言 10.session原理 11.te ...

  7. npm 命令 --save 和 --save-dev 的区别

    回顾 npm install 命令 我们在使用 npm install 安装模块的模块的时候 ,一般会使用下面这几种命令形式: 1 2 3 4 5 6 7 npm install moduleName ...

  8. Codeforces Round #599 (Div. 1) A. Tile Painting 数论

    C. Tile Painting Ujan has been lazy lately, but now has decided to bring his yard to good shape. Fir ...

  9. 怎么在ubuntu下安装使用pycharm

    1.安装jdk 先下载jdk: https://pan.baidu.com/s/1o7MqvKA 解压到本地: 方法一:直接点击右键,点“提取此文件 方法二:使用命令行sudo tar -zxvf j ...

  10. Mybatis和Hibernate框架的区别

    Mybatis和Hibernate框架的区别1 简单简介 1.1 Hibernate 框架 Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,建立对象与数据 ...