普开数据大数据应用实例基于Hadoop的大规模数据排序算法.docx
- 文档编号:30513355
- 上传时间:2023-08-16
- 格式:DOCX
- 页数:22
- 大小:719.09KB
普开数据大数据应用实例基于Hadoop的大规模数据排序算法.docx
《普开数据大数据应用实例基于Hadoop的大规模数据排序算法.docx》由会员分享,可在线阅读,更多相关《普开数据大数据应用实例基于Hadoop的大规模数据排序算法.docx(22页珍藏版)》请在冰豆网上搜索。
普开数据大数据应用实例基于Hadoop的大规模数据排序算法
普开数据大数据应用实例:
基于Hadoop的大规模数据排序算法
基于Hadoop的大规模数据排序
目录
一、前言4
二、Hadoop及Mapreduce的相关介绍4
1.Hadoop4
(1)Hadoop简介4
(2)Hadoop架构5
(3)分布式计算模型5
2.Mapreduce5
(1)mapreduce和hadoop起源5
(2)mapreduce工作流程6
(3)运行环境7
(4)输入与输出7
(5)Map/Reduce-用户界面7
三、大规模数据排序8
1.简介8
2.Nutch9
四、算法分析10
1.Sort算法分析10
(1)排序实例10
(2)运行排序基准测试10
(3)代码分析10
2.Secondsort算法分析12
(1)工作原理12
(2)具体步骤12
(3)SecondarySort.java的部分代码13
3.Terasort算法分析15
(1)概述15
(2)算法思想15
(3)Terasort算法17
五、参考资料19
一、前言
我们小组主要对基于[hadoop的大规模数据排序算法、海量数据的生成做了一定的研究。
我们首先对于hadoop做了初步了解,其次,mapreduce是hadoop的很重要的算法,我们在第二阶段对mapreduce以及一些代码做了分析。
第三阶段,我们安装虚拟机和Linux以及hadoop的软件,配置运行环境。
第四阶段,我们对大规模数据排序进行深入的研究,对nutch进行了简单的了解。
第五阶段,对一些源代码进行分析,主要是排序算法中的sort.java,secondsort.java,terasort。
下面的正文中将作出具体的介绍。
二、Hadoop及Mapreduce的相关介绍
1.Hadoop
(1)Hadoop简介
Hadoop是一个分布式系统基础架构,由Apache基金会开发。
用户可以在不了解分布式底层细节的情况下,开发分布式程序。
充分利用集群的威力高速运算和存储。
Hadoop实现了一个分布式文件系统,简称HDFS。
HDFS有着高容错性的特点,并且设计用来部署在低廉的硬件上。
而且它提供高传输率来访问应用程序的数据,适合那些有着超大数据集的应用程序。
(2)Hadoop架构
图表1hadoop架构
Hadoop有许多元素构成。
其最底部是HDFS,它存储Hadoop集群中所有存储节点上的文件。
HDFS的上一层是MapReduce引擎,该引擎由JobTrackers和TaskTrackers组成。
(3)分布式计算模型
一个hadoop集群往往有几十台甚至成百上千台lowcost的计算机组成,我们运行的每一个任务都要在这些计算机上做任务的分发,执行中间数据排序以及最后的汇总,期间还包含节点发现,任务的重试,故障节点替换等等等等的维护以及异常情况处理。
所以说hadoop就是一个计算模型。
一个分布式的计算模型。
2.Mapreduce
(1)mapreduce和hadoop起源
MapReduce借用了函数式编程的概念,是Google发明的一种数据处理模型。
因为Google几乎爬了互联网上的所有网页,要为处理这些网页并为搜索引擎建立索引是一项非常艰巨的任务,必须借助成千上万台机器同时工作(也就是分布式并行处理),才有可能完成建立索引的任务。
所以,Google发明了MapReduce数据处理模型,而且他们还就此发表了相关论文。
后来,DougCutting老大就根据这篇论文硬生生的复制了一个MapReduce出来,也就是今天的Hadoop。
(2)mapreduce工作流程
MapReduce处理数据过程主要分成2个阶段:
map阶段和reduce阶段。
先执行map阶段,再执行reduce阶段。
①在正式执行map函数前,需要对输入进行“分片”(就是将海量数据分成大概相等的“块”,hadoop的一个分片默认是64M),以便于多个map同时工作,每一个map任务处理一个“分片”。
②分片完毕后,多台机器就可以同时进行map工作了。
map函数要做的事情,相当于对数据进行“预处理”,输出所要的“关切”。
map对每条记录的输出以
③在进入reduce阶段之前,要将各个map中相关的数据(key相同的数据)归结到一起,发往一个reducer。
这里面就涉及到多个map的输出“混合地”对应多个reducer的情况,这个过程叫做“洗牌”。
④接下来进入reduce阶段。
相同的key的map输出会到达同一个reducer。
reducer对key相同的多个value进行“reduce操作”,最后一个key的一串value经过reduce函数的作用后,变成了一个value。
图表2mapreduce简单工作流程
(3)运行环境
·HadoopStreaming是一种运行作业的实用工具,它允许用户创建和运行任何可执行程序(例如:
Shell工具)来做为mapper和reducer。
·HadoopPipes是一个与SWIG兼容的C++API(没有基于JNITM技术),它也可用于实现Map/Reduce应用程序。
(4)输入与输出
Map/Reduce框架运转在
框架需要对key和value的类(class)进行序列化操作,因此,这些类需要实现Writable接口。
另外,为了方便框架执行排序操作,key类必须实现WritableComparable接口。
一个Map/Reduce作业的输入和输出类型如下所示:
(input)
(5)Map/Reduce-用户界面
这部分文档为用户将会面临的Map/Reduce框架中的各个环节提供了适当的细节。
这应该会帮助用户更细粒度地去实现、配置和调优作业。
然而,需要注意每个类/接口的javadoc文档提供最全面的文档。
我们会先看看Mapper和Reducer接口。
应用程序通常会通过提供map和reduce方法来实现它们。
然后,我们会讨论其他的核心接口,其中包括:
JobConf,JobClient,Partitioner,OutputCollector,Reporter,InputFormat,OutputFormat等等。
最后,我们将通过讨论框架中一些有用的功能点(例如:
DistributedCache,IsolationRunner等等)来收尾。
三、大规模数据排序
1.简介
使用hadoop进行大量的数据排序排序最直观的方法是把文件所有内容给map之后,map不做任何处理,直接输出给一个reduce,利用hadoop的自己的shuffle机制,对所有数据进行排序,而后由reduce直接输出。
然而这样的方法跟单机毫无差别,完全无法用到多机分布式计算的便利。
因此这种方法是不行的。
利用hadoop分而治之的计算模型,可以参照快速排序的思想。
在这里我们先简单回忆一下快速排序。
快速排序基本步骤就是需要现在所有数据中选取一个作为支点。
然后将大于这个支点的放在一边,小于这个支点的放在另一边。
设想如果我们有N个支点(这里可以称为标尺),就可以把所有的数据分成N+1个part,将这N+1个part丢给reduce,由hadoop自动排序,最后输出N+1个内部有序的文件,再把这N+1个文件首尾相连合并成一个文件,收工。
由此我们可以归纳出这样一个用hadoop对大量数据排序的步骤:
①对待排序数据进行抽样;
②对抽样数据进行排序,产生标尺;
③Map对输入的每条数据计算其处于哪两个标尺之间;将数据发给对应区间ID的reduce
④Reduce将获得数据直接输出。
这里使用对一组url进行排序来作为例子:
图表3url排序
如何将数据发给一个指定ID的reduce?
hadoop提供了多种分区算法。
这些算法根据map输出的数据的key来确定此数据应该发给哪个reduce(reduce的排序也依赖key)。
因此,如果需要将数据发给某个reduce,只要在输出数据的同时,提供一个key(在上面这个例子中就是reduce的ID+url),数据就该去哪儿去哪儿了。
2.Nutch
Nutch是一个由Java实现的,刚刚诞生开放源代码(open-source)的web搜索引擎。
Nutch主要分为爬虫crawler和查询searcher两部分。
Crawler主要用于从网络上抓取网页并为这些网页建立索引。
Searcher主要利用这些索引检索用户的查找关键词来产生查找结果。
两者之间的接口是索引,所以除去索引部分,两者之间的耦合度很低。
Crawler的重点在两个方面,Crawler的工作流程和涉及的数据文件的格式和含义。
Crawler的工作原理:
首先Crawler根据WebDB生成一个待抓取网页的URL集合叫做Fetchlist,接着下载线程Fetcher根据Fetchlist将网页抓取回来,如果下载线程有很多个,那么就生成很多个Fetchlist,也就是一个Fetcher对应一个Fetchlist。
然后Crawler用抓取回来的网页更新WebDB,根据更新后的WebDB生成新的Fetchlist,里面是未抓取的或者新发现的URLs,然后下一轮抓取循环重新开始。
四、算法分析
1.Sort算法分析
(1)排序实例
排序实例仅仅用map/reduce框架来把输入目录排序放到输出目录。
输入和输出必须是顺序文件,键和值是BytesWritable.mapper是预先定义的IdentityMapper,reducer是预先定义的IdentityReducer,两个都是把输入直接的输出。
要运行这个例子:
bin/hadoopjarhadoop-*-examples.jarsort[-m<#maps>][-r<#reduces>]
(2)运行排序基准测试
为了使得排序例子作为一个基准测试,用RandomWriter产生10GB/node的数据。
然后用排序实例来进行排序。
这个提供了一个可扩展性依赖于集群的大小的排序基准。
默认情况下,排序实例用1.0*capacity作为reduces的数量,依赖于你的集群的大小你可能会在1.75*capacity的情况下得到更好的结果。
(3)代码分析
在eclipse中设置参数:
/home/hadoop/rand/part-00000/home/hadoop/rand-sort
其中/home/hadoop/rand/part-00000表示输入路径,/home/hadoop/rand-sort表示输出路径。
数据来源
我们这里输入参数中的“/home/hadoop/rand/part-00000”是通过hadoop实例RandomWriter这个实例得到的。
为了节省时间,hadoop实例RandomWriter中得到了两个文件,我们这里指使用了一个文件part-00000。
如果要对两个文件都进行排序操作,那么输入路径只需要是目录即可。
Sort算法源代码
a)源码位置
/local/zkl/hadoop/hadoop-0.20.1/hadoop-0.20.1/src/examples/org/apache/hadoop/examples/Sort.java
b)下面程序是一段关于Sort算法的源代码:
26.*Torun:
bin/hadoopjarbuild/hadoop-examples.jarsort
27.*[-mmaps][-rreduces]
28.*[-inFormatinputformatclass]
29.*[-outFormatoutputformatclass]
30.*[-outKeyoutputkeyclass]
31.*[-outValueoutputvalueclass]
32.*[-totalOrderpcntnumsamplesmaxsplits]
33.*in-dirout-dir
34.*/
35.publicclassSort
36.privateRunningJobjobResult=null;
37.
166.//inputattr:
/home/hadoop/rand/part-00000/home/hadoop/rand-sort
167.
168.publicstaticvoidmain(String[]args)throwsException{
169.intres=ToolRunner.run(newConfiguration(),newSort(),args);
170.System.exit(res);
171.}
172.
173./**
174.*Getthelastjobthatwasrunusingthisinstance.
175.*@returntheresultsofthelastjobthatwasrun
176.*/
177.publicRunningJobgetResult(){
178.returnjobResult;
179.}
180.}
2.Secondsort算法分析
(1)工作原理
在map阶段,使用job.setInputFormatClass定义的InputFormat将输入的数据集分割成小数据块splites,同时InputFormat提供一个RecordReder的实现。
本例子中使用的是TextInputFormat,他提供的RecordReder会将文本的一行的行号作为key,这一行的文本作为value。
这就是自定义Map的输入是
然后调用自定义Map的map方法,将一个个
注意输出应该符合自定义Map中定义的输出
最终是生成一个List
在map阶段的最后,会先调用job.setPartitionerClass对这个List进行分区,每个分区映射到一个reducer。
每个分区内又调用job.setSortComparatorClass设置的key比较函数类排序。
可以看到,这本身就是一个二次排序。
如果没有通过job.setSortComparatorClass设置key比较函数类,则使用key的实现的compareTo方法。
在第一个例子中,使用了IntPair实现的compareTo方法,而在下一个例子中,专门定义了key比较函数类。
在reduce阶段,reducer接收到所有映射到这个reducer的map输出后,也是会调用job.setSortComparatorClass设置的key比较函数类对所有数据对排序。
然后开始构造一个key对应的value迭代器。
这时就要用到分组,使用jobjob.setGroupingComparatorClass设置的分组函数类。
只要这个比较器比较的两个key相同,他们就属于同一个组,它们的value放在一个value迭代器,而这个迭代器的key使用属于同一个组的所有key的第一个key。
最后就是进入Reducer的reduce方法,reduce方法的输入是所有的(key和它的value迭代器)。
同样注意输入与输出的类型必须与自定义的Reducer中声明的一致。
二次排序就是首先按照第一字段排序,然后再对第一字段相同的行按照第二字段排序,注意不能破坏第一次排序的结果。
(2)具体步骤
●自定义key。
在mr中,所有的key是需要被比较和排序的,并且是二次,先根据partitione,再根据大小。
而本例中也是要比较两次。
先按照第一字段排序,然后再对第一字段相同的按照第二字段排序。
根据这一点,我们可以构造一个复合类IntPair,他有两个字段,先利用分区对第一字段排序,再利用分区内的比较对第二字段排序。
●由于key是自定义的,所以还需要自定义一下类:
分区函数类;key比较函数类;分组函数类。
(3)SecondarySort.java的部分代码
c)源码位置
/local/zkl/hadoop/hadoop-0.20.1/hadoop-0.20.1/src/examples/org/apache/hadoop/examples/SecondarySort.java
d)下面程序是一段关于secondarySort的源代码:
33.publicclassSecondarySort{
34.//自己定义的key类应该实现WritableComparable接口
35.publicstaticclassIntPair
36.implementsWritableComparable{
37.privateintfirst=0;
38.privateintsecond=0;
39.
40./**
41.*Settheleftandrightvalues.
42.*/
43.publicvoidset(intleft,intright){
44.first=left;
45.second=right;
46.}
47.publicintgetFirst(){
48.returnfirst;
49.}
50.publicintgetSecond(){
51.returnsecond;
52.}
53./
54.@Override
55.//反序列化,从流中的二进制转换成IntPair
56.publicvoidreadFields(DataInputin)throwsIOException{
57.first=in.readInt()+Integer.MIN_VALUE;
58.second=in.readInt()+Integer.MIN_VALUE;
59.}
60.@Override
61.//序列化,将IntPair转化成使用流传送的二进制
62.publicvoidwrite(DataOutputout)throwsIOException{
63.out.writeInt(first-Integer.MIN_VALUE);
64.out.writeInt(second-Integer.MIN_VALUE);
65.}
66.//新定义类应该重写的两个方法
67.@Override
68.//ThehashCode()methodisusedbytheHashPartitioner(thedefaultpartitionerinMapReduce)
185.//主函数
186.publicstaticvoidmain(String[]args)throwsException{
187.//TODOAuto-generatedmethodstub
188.//读取hadoop配置
189.Configurationconf=newConfiguration();
190.String[]otherArgs=newGenericOptionsParser(conf,args).getRemainingArgs();
191.if(otherArgs.length!
=2){
192.System.err.println("Usage:
secondarysrot");
193.System.exit
(2);
194.}
195.//实例化一道作业
196.Jobjob=newJob(conf,"secondarysort");
197.job.setJarByClass(SecondarySort.class);
198.//Mapper类型
199.job.setMapperClass(MapClass.class);
200.//Reducer类型
201.job.setReducerClass(Reduce.class);
202.//分区函数
203.job.setPartitionerClass(FirstPartitioner.class);
204.//分组函数
205.job.setGroupingComparatorClass(FirstGroupingComparator.class);
206.//map输出Key的类型
207.job.setMapOutputKeyClass(IntPair.class);
208.//map输出Value的类型
209.job.setMapOutputValueClass(IntWritable.class);
210.//rduce输出Key的类型
211.job.setOutputKeyClass(Text.class);
212.//rduce输出Value的类型
213.job.setOutputValueClass(IntWritable.class);
214.//输入hdfs路径
215.FileInputFormat.addInputPath(job
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 数据 应用 实例 基于 Hadoop 大规模 排序 算法