MapReduce编程规范:

(1)用户编写的程序分成三个部分:Mapper,Reducer,Driver(提交运行mr程序的客户端)

(2)Mapper的输入数据是KV对的形式(KV的类型可自定义)

(3)Mapper的输出数据是KV对的形式(KV的类型可自定义)

(4)Mapper中的业务逻辑写在map()方法中

(5)map()方法(maptask进程)对每一个<K,V>调用一次

(6)Reducer的输入数据类型对应Mapper的输出数据类型,也是KV

(7)Reducer的业务逻辑写在reduce()方法中

(8)Reducetask进程对每一组相同k的<k,v>组调用一次reduce()方法

(9)用户自定义的Mapper和Reducer都要继承各自的父类

(10)整个程序需要一个Drvier来进行提交,提交的是一个描述了各种必要信息的job对象

WordCount:在给定的文本文件中统计输出每一个单词出现的总次数

 package com.ahu.bigdata.mr;

 import java.io.IOException;

 import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.IntWritable;
import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Job;
import org.apache.hadoop.mapreduce.Mapper;
import org.apache.hadoop.mapreduce.Reducer;
import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat; /**
* 在给定的文本文件中统计出每一个单词出现的总次数
*
* @author ahu_lichang
*
*/
public class WordCountDriver {
/**
* 自定义mapper类
*
* @author ahu_lichang
*
*/
static class WordCountMapper extends
Mapper<LongWritable, Text, Text, IntWritable> {
// map方法的生命周期:框架每传一行数据就被调用一次
// key:这一行的起始点在文件中的偏移量
// value:这一行的内容
@Override
protected void map(LongWritable key, Text value, Context context)
throws IOException, InterruptedException {
// 拿到一行数据转换为String
String line = value.toString();
// 将这一行切分出各个单词
String[] words = line.split("\t");
// 遍历数组,输出<单词,1>
for (String word : words) {
context.write(new Text(word), new IntWritable(1));
}
}
} /**
* 自定义一个reducer类
*
* @author ahu_lichang
*
*/
static class WordCountReducer extends
Reducer<Text, IntWritable, Text, IntWritable> {
// reduce生命周期:框架每传递进来一个KV组,reduce方法就被调用一次
@Override
protected void reduce(Text key, Iterable<IntWritable> values,
Context context) throws IOException, InterruptedException {
// 定义一个计数器
int count = 0;
// 遍历这一组KV的所有V,累加到count中
for (IntWritable value : values) {
count += value.get();
}
context.write(key, new IntWritable(count));
}
} private static final String INPUT_PATH = "hdfs://hadoop1:9000/data.txt";
private static final String OUT_PATH = "hdfs://hadoop1:9000/wcoutput"; // WordCountDriver是一个主类,用来描述job并提交job
// 相当于一个yarn集群的客户端
// 需要在此封装我们的mr程序的相关运行参数,指定jar包
// 最后提交给yarn
public static void main(String[] args) throws Exception {
if (args == null || args.length == 0) {
args = new String[2];
args[0] = INPUT_PATH;
args[1] = OUT_PATH;
}
// 把业务逻辑相关的信息(哪个是mapper,哪个是reducer,要处理的数据在哪里,输出的结果放在哪里...)描述成一个job对象
// 把这个描述好的job提交给集群去运行
Configuration conf = new Configuration();
Job job = Job.getInstance(conf); // 指定这个job所在的jar包
// job.setJar("/usr/local/wordcount.jar");
job.setJarByClass(WordCountDriver.class); job.setMapperClass(WordCountMapper.class);
job.setReducerClass(WordCountReducer.class); // 设置业务逻辑Mapper类的输出key和value的数据类型
job.setMapOutputKeyClass(Text.class);
job.setMapOutputValueClass(IntWritable.class); // 设置业务逻辑Reducer类的输出key和value的数据类型
job.setOutputKeyClass(Text.class);
job.setOutputValueClass(IntWritable.class); // 指定job的输入原始文件所在目录
//FileInputFormat.setInputPaths(job, new Path(INPUT_PATH));
FileInputFormat.setInputPaths(job, new Path(args[0]));
// 指定job的输出结果所在目录
//FileOutputFormat.setOutputPath(job, new Path(OUT_PATH));
FileOutputFormat.setOutputPath(job, new Path(args[1])); // 将job中配置的相关参数,以及job所用的java类所在的jar包,提交给yarn集群去运行
/* job.submit(); */
boolean res = job.waitForCompletion(true);
System.exit(res ? 0 : 1); } }

1、先在eclipse工程中创建一个用户类库hadoop264jar,将hadoop安装目录中的share文件夹中的common、hdfs、MapReduce、yarn中的jar包全部添加进去。

2、书写代码:创建一个mapper自定义类,在创建一个reducer自定义类,最后创建一个描述job并提交job的主类。

3、运行方式有两种:

      (1)直接在eclipse中运行。但是会出现个权限拒绝错误,那是因为没有身份标识造成的。这里再介绍第二种身份标识方式:(第一种身份标识方式,见《HDFS详解》)

        

      (2)在集群上打包运行。先将书写好的代码打成jar包,然后将wordcount.jar复制到Linux的/usr/local/目录下,然后就可以在命令行中运行了。

        hadoop jar /usr/local/wordcount.jar /data.txt /wcout

        

MapReduce程序运行模式:

1、本地运行模式

2、集群运行模式

MapReduce中的Combiner(归约)《Combiner》里面有代码示例

(1)combiner是MR程序中Mapper和Reducer之外的一种组件

(2)combiner组件的父类就是Reducer

(3)combiner和reducer的区别在于运行的位置:

    Combiner是在每一个maptask所在的节点运行

    Reducer是接收全局所有Mapper的输出结果;

(4) combiner的意义就是对每一个maptask的输出进行局部汇总,以减小网络传输量

具体实现步骤:

  1、 自定义一个combiner继承Reducer,重写reduce方法

  2、 在job中设置:  job.setCombinerClass(CustomCombiner.class)

(5) combiner能够应用的前提是不能影响最终的业务逻辑。而且,combiner的输出kv应该跟reducer的输入kv类型要对应起来

注意:

Combiner的使用要非常谨慎

因为combiner在mapreduce过程中可能调用也可能不调用,可能调一次也可能调多次

所以:combiner使用的原则是:有或没有都不能影响业务逻辑

MapReduce实战1的更多相关文章

  1. MapReduce实战:统计不同工作年限的薪资水平

    1.薪资数据集 我们要写一个薪资统计程序,统计数据来自于互联网招聘hadoop岗位的招聘网站,这些数据是按照记录方式存储的,因此非常适合使用 MapReduce 程序来统计. 2.数据格式 我们使用的 ...

  2. mapreduce实战:统计美国各个气象站30年来的平均气温项目分析

    气象数据集 我们要写一个气象数据挖掘的程序.气象数据是通过分布在美国各地区的很多气象传感器每隔一小时进行收集,这些数据是半结构化数据且是按照记录方式存储的,因此非常适合使用 MapReduce 程序来 ...

  3. MapReduce实战--倒排索引

    本文地址:http://www.cnblogs.com/archimedes/p/mapreduce-inverted-index.html,转载请注明源地址. 1.倒排索引简介 倒排索引(Inver ...

  4. MapReduce实战(三)分区的实现

    需求: 在实战(一)的基础 上,实现自定义分组机制.例如根据手机号的不同,分成不同的省份,然后在不同的reduce上面跑,最后生成的结果分别存在不同的文件中. 对流量原始日志进行流量统计,将不同省份的 ...

  5. MapReduce实战:邮箱统计及多输出格式实现

    紧接着上一篇博文我们学习了MapReduce得到输出格式之后,在这篇博文里,我们将通过一个实战小项目来熟悉一下MultipleOutputs(多输出)格式的用法. 项目需求: 假如这里有一份邮箱数据文 ...

  6. MapReduce实战项目:查找相同字母组成的字谜

    实战项目:查找相同字母组成的字谜 项目需求:一本英文书籍中包含有成千上万个单词或者短语,现在我们要从中找出相同字母组成的所有单词. 数据集和期望结果举例: 思路分析: 1)在Map阶段,对每个word ...

  7. 《OD大数据实战》MapReduce实战

    一.github使用手册 1. 我也用github(2)——关联本地工程到github 2. Git错误non-fast-forward后的冲突解决 3. Git中从远程的分支获取最新的版本到本地 4 ...

  8. 【原创】MapReduce实战(一)

    应用场景: 用户每天会在网站上产生各种各样的行为,比如浏览网页,下单等,这种行为会被网站记录下来,形成用户行为日志,并存储在hdfs上.格式如下: 17:03:35.012ᄑpageviewᄑ{&qu ...

  9. MapReduce实战(七)GroupingComparator

    需求: Order_0000001,Pdt_01,222.8Order_0000001,Pdt_05,25.8Order_0000002,Pdt_05,325.8Order_0000002,Pdt_0 ...

随机推荐

  1. [JZOJ 5402] God Knows

    终于搞完了这乡里别题目 $ $ 考虑一个 \(dp\) ,设 \(f[i]\) 表示最后一个匹配选 \((i,p[i])\) 的最小费用 首先我们考虑答案长什么样 假设根据 \(p[i]\) 排序 , ...

  2. 【POJ2796】Feel Good 单调栈

    题目大意:给定一个长度为 N 的序列,求任意区间 [ l , r ] 中最小的\(min\{v[i],i\in[l,r] \}*\Sigma_{i=l}^rv[i]\). 题解:这是一道具有标准单调栈 ...

  3. Python之旅:并发编程之协程

    一 引子 本节的主题是基于单线程来实现并发,即只用一个主线程(很明显可利用的cpu只有一个)情况下实现并发,为此我们需要先回顾下并发的本质:切换+保存状态 cpu正在运行一个任务,会在两种情况下切走去 ...

  4. postgresql常见命令及操作

    pgsql已经更新到beta11了,不同版本的服务器启动或相关命令.配置可能会有不同,所以得根据pg版本进行操作.下面记录一些工作中常用到的一些操作,主要包括服务启动.备份/恢复数据.数据目录迁移.常 ...

  5. sqlite3数据库的简要应用

    Sqlite3数据库升级方案的变化. 1,  若是讲要升级的数据库版本更高,则从低版本数据库中拷贝与新数据库相同字段的内容,其他字段按照默认值创建.A->B->C这样逐个版本升级,每个版本 ...

  6. starUML的使用方法和各种线条的含义

    使用方法https://www.cnblogs.com/syncCN/p/5433746.html 各种线条的含义:https://www.cnblogs.com/huaxingtianxia/p/6 ...

  7. Kafka 温故(四):Kafka的安装

    Step 1: 下载Kafka > tar -xzf kafka_2.9.2-0.8.1.1.tgz> cd kafka_2.9.2-0.8.1.1 Step 2: 启动服务Kafka用到 ...

  8. AngularJS入门基础——表达式

    表达式在AngularJS应用中广泛的使用,因此深入理解AngularJS如何使用并运算表达式是非常重要的.   表达式和eval非常相似,但是由于表达式由AngularJS来处理,它们有已下显著不同 ...

  9. HDU 2093 考试排名 模拟题

    解题报告: 题目描述:写一个程序给一个编程考试C++实时提交系统排名,给你的数据是题目的总数,每次错误提交罚的时间分,每位用户的姓名,然后是输入用户每题的完成情况,有一下几种情况,第一,输入只有一个正 ...

  10. 为什么今天的L4无人驾驶无法到达终局(转)

    本文来自于公众号驭势未来,是驭势科技的微信公众平台,本博客收录的这篇文章版权作者吴甘沙,博客中仅对部分内容进行编辑. 作者:吴甘沙 原文链接:here 声明:文中的观点只代表版权作者的观点,本转载不涉 ...