参考: http://apps.hi.baidu.com/share/detail/31363777
在爬虫启动工作的过程中,我们不希望同一个网页被多次下载,因为重复下载不仅会浪费CPU机时,还会为搜索引擎系统增加负荷。而想要控制这种重复性下载问题,就要考虑下载所依据的超链接,只要能够控制待下载的URL不重复,基本可以解决同一个网页重复下载的问题。
非常容易想到,在搜索引擎系统中建立一个全局的专门用来检测,是否某一个URL对应的网页文件曾经被下载过的URL存储库,这就是方案。
接着要考虑的就是如何能够更加高效地让爬虫工作,确切地说,让去重工作更加高效。如果实现去重,一定是建立一个URL存储库,并且已经下载完成的URL在进行检测时候,要加载到内存中,在内存中进行检测一定会比直接从磁盘上读取速度快很多。
我们先从最简单的情况说起,然后逐步优化,最终得到一个非常不错的解决方案。
第一,基于磁盘的顺序存储。
这里,就是指把每个已经下载过的URL进行顺序存储。你可以把全部已经下载完成的URL存放到磁盘记事本文件中。每次有一个爬虫线程得到一个任务URL开始下载之前,通过到磁盘上的该文件中检索,如果没有出现过,则将这个新的URL写入记事本的最后一行,否则就放弃该URL的下载。
这种方式几乎没有人考虑使用了,但是这种检查的思想是非常直观的。试想,如果已经下载了100亿网页,那么对应着100亿个链接,也就是这个检查URL是否重复的记事本文件就要存储这100亿URL,况且,很多URL字符串的长度也不小,占用存储空间不说,查找效率超级低下,这种方案肯定放弃。
第二,基于Hash算法的存储。
对每一个给定的URL,都是用一个已经建立好的Hash函数,映射到某个物理地址上。当需要进行检测URL是否重复的时候,只需要将这个URL进行Hash映射,如果得到的地址已经存在,说明已经被下载过,放弃下载,否则,将该URL及其Hash地址作为键值对存放到Hash表中。
这样,URL去重存储库就是要维护一个Hash表,如果Hash函数设计的不好,在进行映射的时候,发生碰撞的几率很大,则再进行碰撞的处理也非常复杂。而且,这里使用的是URL作为键,URL字符串也占用了很大的存储空间。
第三,基于MD5压缩映射的存储。
MD5算法是一种加密算法,同时它也是基于Hash的算法。这样就可以对URL字符串进行压缩,得到一个压缩字符串,同时可以直接得到一个Hash地址。另外,MD5算法能够将任何字符串压缩为128位整数,并映射为物理地址,而且MD5进行Hash映射碰撞的几率非常小,这点非常好。从另一个方面来说,非常少的碰撞,对于搜索引擎的爬虫是可以容忍的。况且,在爬虫进行检测的过程中,可以通过记录日志来保存在进行MD5时发生碰撞的URL,通过单独对该URL进行处理也是可行的。
下面就是是对URL进行压缩的MD5方法,对URL字符串进行压缩:
public static String md5(String string) {
char hexDigits[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd',
'e', 'f' };
try {
byte[] bytes = string.getBytes();
MessageDigest messageDigest = MessageDigest.getInstance("MD5");
messageDigest.update(bytes);
byte[] updateBytes = messageDigest.digest();
int len = updateBytes.length;
char myChar[] = new char[len * 2];
int k = 0;
for (int i = 0; i < len; i++) {
byte byte0 = updateBytes[i];
myChar[k++] = hexDigits[byte0 >>> 4 & 0x0f];
myChar[k++] = hexDigits[byte0 & 0x0f];
}
return new String(myChar);
} catch (Exception e) {
return null;
}
}
在Java中有一个Map类非常好,你可以将压缩后的URL串作为Key,而将Boolean作为Value进行存储,然后将工作中的Map在爬虫停止工作后序列化到本地磁盘上;当下一次启动新的爬虫任务的时候,再将这个Map反序列化到内存中,供爬虫进行URL去重检测。
第四,基于嵌入式Berkeley DB的存储。
Berkeley DB的特点就是只存储键值对类型数据,这和URL去重有很大关系。去重,可以考虑对某个键,存在一个值,这个值就是那个键的状态。
使用了Berkeley DB,你就不需要考虑进行磁盘IO操作的性能损失了,这个数据库在设计的时候很好地考虑了这些问题,并且该数据库支持高并发,支持记录的顺序存储和随机存储,是一个不错的选择。
URL去重存储库使用Berkeley DB,压缩后的URL字符串作为Key,或者直接使用压缩后的URL字节数组作为Key,对于Value可以使用Boolean,一个字节,或者使用字节数组,实际Value只是一个状态标识,减少Value存储占用存储空间。
第五,基于布隆过滤器(Bloom Filter)的存储。
使用布隆过滤器,设计多个Hash函数,也就是对每个字符串进行映射是经过多个Hash函数进行映射,映射到一个二进制向量上,这种方式充分利用了比特位。
不过,我没有用过这种方式,有机会可以尝试一下。可以参考Google的http://www.googlechinablog.com/2007/07/bloom-filter.html。
分享到:
相关推荐
通过研究目标网站爬虫门槛的协商及通过的条件,及反爬虫相关技术及最新发展,设计并实现了一个完整的网络爬虫,最终完成了对目标网站所有文章数据的提取和存储。同时,通过对实验室内部网站的测试实现了绕过反爬虫...
10. 防止重复爬取:可能使用URL去重策略,如将已爬取过的URL存入数据库,避免重复抓取同一页面。 11. 错误处理和重试机制:项目中会包含异常处理代码,当遇到网络问题或网站结构变化时,能自动进行错误恢复或重试,...
1993年,麻省理工学院的马休·格雷(Matthew Gray)编写了世界上第一个网络爬虫——“互联网漫游者”(Wanderer)。随着互联网的发展,网络爬虫的功能与复杂度不断提升,成为现代搜索引擎和大数据分析的重要组成部分...
《信息内容安全》课程设计——搜索引擎 在信息技术领域,搜索引擎是一个至关重要的工具,它使得海量信息的检索变得高效且便捷。本次课程设计的核心是构建一个基础的搜索引擎,以理解和实践信息内容安全的相关知识。...
本文将深入探讨搜索引擎的工作原理,特别是其中的关键步骤——网络爬虫技术。 #### 一、搜索引擎工作流程 搜索引擎的工作流程可以分为三个主要步骤: 1. **从互联网上抓取网页**:这个过程通常由网络爬虫(Spider...
这个模块可能会实现以下功能:URL去重,防止重复爬取同一页面;URL的解析和提取,从HTML源码中找出所有链接;错误处理,对无效或无法访问的URL进行异常处理;以及URL的分发,按照某种策略(如深度优先、广度优先)将...
- **哈希表(Hash Table)**:用于快速查找和存储URL,提高URL去重效率。 - **优先队列(Priority Queue)**:如果实现深度优先或基于优先级的爬取策略,可能会用到优先队列。 4. **网络编程** - **套接字...
这篇文档将深入探讨中北大学大三课程设计项目——一个基于Python的爬虫程序,该项目不仅包含源代码,还提供了数据处理结果、需求分析和方案设计报告。通过这个项目,学生能够掌握网络爬虫的基本原理和实践应用,同时...
二、Python爬虫框架——JerryWebSpider “jerryWebSpider-master”很可能是一个定制化的Python爬虫框架,Python是爬虫开发的常用语言,因为其语法简洁且有许多强大的库如BeautifulSoup、Scrapy等。该框架可能包含了...
在Python开发领域,Web爬虫是获取大量网络数据的重要工具。自定义爬虫框架允许开发者根据特定需求构建高效、可维护的爬虫项目,以适应不同网站的数据抓取挑战。本教程将深入探讨如何设计并实现一个订制的Python爬虫...
本文将深入探讨一个基于Python的开源爬虫框架——Scrapy,以及如何利用它来构建爬虫项目,将抓取的数据存储到MySQL数据库或文件中。Scrapy是一个强大的、高效的爬虫框架,广泛应用于网页数据抓取和信息提取。 ### ...
4. **URL去重与队列管理**:为了避免重复抓取同一页面,爬虫会检查新提取的URL是否已存在于抓取队列中。如果不在,就将其加入队列,准备下一次抓取。 5. **深度优先/广度优先策略**:爬虫可以按照深度优先或广度...
通过分析`<a>`标签,爬虫可以收集所有链接,并可能进行去重处理,避免重复抓取同一个页面。这些URLs随后会被分类,例如按照它们与主题的相关性排序,或者按照它们在网站结构中的位置。 4. **URL地址分类与数据库...
《Python1903笔记——深入理解Web爬虫(Spider)》 在Python的世界里,爬虫(Spider)是用于自动化获取网页数据的重要工具。Python1903笔记中的"12-spider"部分,主要涵盖了如何构建和使用Python爬虫进行网络数据...
2. **URL管理器(URLManager)**:URL管理器主要负责URL的存储和去重。它使用Python的`set`数据结构,其中包含两个集合,一个存储新发现但未爬取的URL(`newurlset`),另一个存储已经爬取过的URL(`oldurlset`)。...
6. **数据存储与处理**:爬取到的源码数据可能需要进行清洗、去重、存储等处理,以便后续分析和使用。这可能涉及数据库操作和数据清洗技巧。 总的来说,"基于ASP的网络直播电视源码爬取 v1.0.zip"项目结合了ASP技术...
这可能涉及到URL的存储、去重和递归访问。 4. **下载模块**:一旦找到PDF链接,爬虫会使用`requests`的下载功能或其他下载工具,如`wget`,将文件保存到本地。 5. **异常处理**:爬虫需要处理可能出现的网络错误、...
搜索引擎是一种特殊的软件系统,它通过自动或半自动的方式在网络上搜集网页信息,对其进行索引处理,并存储起来。当用户输入关键词进行查询时,搜索引擎能够迅速地从索引中检索出相关网页并按一定顺序呈现给用户。 ...
总的来说,MyWebCrawler是一个基于Java的网页爬虫,它使用了Jsoup库解析HTML,可能采用了多线程技术提高爬取速度,并遵循一定的网络爬虫规范来收集和存储数据。这个项目为理解网页爬虫的基本原理和实践提供了一个...