大数据笔记(十)——Shuffle与MapReduce编程案例(A)
一.什么是Shuffle
yarn-site.xml文件配置的时候有这个参数:yarn.nodemanage.aux-services:mapreduce_shuffle
因为mapreduce程序运行在nodemanager上,nodemanager运行mapreduce程序的方式就是shuffle。
1.首先,数据在HDFS上是以数据块的形式保存,默认大小128M。
2.数据块对应成数据切片送到Mapper。默认一个数据块对应一个数据切块。
3.Mapper阶段
4.Mapper处理完,写到内存中作缓冲(环形缓冲区,默认100M)
5.内存满80%就发生溢写,进行一次IO操作,写到HDFS的文件系统上。
6.作一个处理,将小文件合成一个大文件
7.Combiner:在Mapper端先做一次Reducer,做一个合并操作
8.将Combiner的数据放到Reducer
9.输出到HDFS
图解:

Maprecue的缺点:发生的IO次数太多(图示标号),严重影响性能。
解决方式:Spark(基于内存)
二.MapReduce编程案例
1.多表查询:等值连接
查询员工信息:部门名称、员工姓名
实现SQL语句:在emp表,dept表联合查询,查询每个部门下面的员工
select d.dname,e.ename
from emp e,dept d
where e.deptno=d.deptno;
分析:

使用MR实现等值连接的分析流程:

程序:
MultiTableQueryMapper.java
package demo.multiTable; import java.io.IOException; import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Mapper;
//k2 部门号 v2 部门名称
public class MultiTableQueryMapper extends Mapper<LongWritable, Text, LongWritable, Text> { @Override
protected void map(LongWritable key1, Text value1, Context context)
throws IOException, InterruptedException {
//数据:可能是部门,也可能是员工
String data = value1.toString();
//分词
String[] words = data.split(",");
//判断数组的长度
if (words.length == 3) {
//部门表:部门号 部门名称
context.write(new LongWritable(Long.parseLong(words[0])), new Text("*"+words[1]));
}else {
//员工表:部门号 员工名称
context.write(new LongWritable(Long.parseLong(words[7])), new Text(words[1]));
}
} }
MultiTableQueryReducer.java
package demo.multiTable; import java.io.IOException; import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Reducer; public class MultiTableQueryReducer extends Reducer<LongWritable, Text, Text, Text> { @Override
protected void reduce(LongWritable k3, Iterable<Text> v3, Context context)
throws IOException, InterruptedException {
//定义变量:保存 部门名称和员工姓名
String dname = "";
String empNameList = ""; for (Text text : v3) {
String string = text.toString();
//找到* 号的位置
int index = string.indexOf("*");
if (index >= 0) {
//代表的是部门名称
dname = string.substring(1);
}else {
//代表的是员工姓名
empNameList = string + ";" + empNameList;
}
} //输出 部门名字 员工姓名字符串
context.write(new Text(dname), new Text(empNameList));
} }
MultiTableQueryMain.java
package demo.multiTable; import java.io.IOException; import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.DoubleWritable;
import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Job;
import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat; public class MultiTableQueryMain { public static void main(String[] args) throws Exception {
Job job = Job.getInstance(new Configuration()); job.setJarByClass(MultiTableQueryMain.class); job.setMapperClass(MultiTableQueryMapper.class);
job.setMapOutputKeyClass(LongWritable.class);
job.setMapOutputValueClass(Text.class); job.setReducerClass(MultiTableQueryReducer.class);
job.setOutputKeyClass(Text.class);
job.setOutputValueClass(Text.class); FileInputFormat.setInputPaths(job, new Path(args[0]));
FileOutputFormat.setOutputPath(job, new Path(args[1])); job.waitForCompletion(true);
} }
结果:

2.多表查询:自连接
自连接:通过表的别名,将同一张表看成多张表
需求:查询一个表内老板姓名和对应的员工姓名
实现SQL语句:
select b.ename,e.ename
from emp b,emp e
where b.empno=e.mgr;
分析:

实现:
SelfJoinMapper.java
package demo.selfJoin; import java.io.IOException; import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Mapper; public class SelfJoinMapper extends Mapper<LongWritable, Text, LongWritable, Text> { @Override
protected void map(LongWritable key1, Text value1, Context context)
throws IOException, InterruptedException {
//7698,BLAKE,MANAGER,7839,1981/5/1,2850,30
String data = value1.toString(); //分词
String[] words = data.split(","); //输出
//1.作为老板表
context.write(new LongWritable(Long.parseLong(words[0])), new Text("*"+words[1])); //2.作为员工表
try{
context.write(new LongWritable(Long.parseLong(words[3])), new Text(words[1]));
}catch(Exception e){
//老板号为空值
context.write(new LongWritable(-1), new Text(words[1]));
}
} }
SelfJoinReducer.java
package demo.selfJoin; import java.io.IOException; import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Reducer; public class SelfJoinReducer extends Reducer<LongWritable, Text, Text, Text> { @Override
protected void reduce(LongWritable k3, Iterable<Text> v3, Context context)
throws IOException, InterruptedException {
//定义变量:保存老板姓名 员工姓名
String bossName = "";
String empNameList = ""; for (Text text : v3) {
String string = text.toString();
//判断是否存在*号
//*号的作用为了区分是哪张表
int index = string.indexOf("*");
if (index >= 0) {
//老板姓名 去掉*号
bossName = string.substring(1);
}else {
//员工姓名
empNameList = string + ";" + empNameList;
}
} //输出
//如果存在老板和员工 才输出
if (bossName.length() > 0 && empNameList.length() > 0) {
context.write(new Text(bossName), new Text(empNameList));
}
} }
SelfJoinMain.java
package demo.selfJoin; import java.io.IOException; import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Job;
import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat; import demo.multiTable.MultiTableQueryMain;
import demo.multiTable.MultiTableQueryMapper;
import demo.multiTable.MultiTableQueryReducer; public class SelfJoinMain { public static void main(String[] args) throws Exception { Job job = Job.getInstance(new Configuration()); job.setJarByClass(SelfJoinMain.class); job.setMapperClass(SelfJoinMapper.class);
job.setMapOutputKeyClass(LongWritable.class);
job.setMapOutputValueClass(Text.class); job.setReducerClass(SelfJoinReducer.class);
job.setOutputKeyClass(Text.class);
job.setOutputValueClass(Text.class); FileInputFormat.setInputPaths(job, new Path(args[0]));
FileOutputFormat.setOutputPath(job, new Path(args[1])); job.waitForCompletion(true); } }
结果:

大数据笔记(十)——Shuffle与MapReduce编程案例(A)的更多相关文章
- 大数据笔记(九)——Mapreduce的高级特性(B)
二.排序 对象排序 员工数据 Employee.java ----> 作为key2输出 需求:按照部门和薪水升序排列 Employee.java package mr.object; impo ...
- 大数据笔记(八)——Mapreduce的高级特性(A)
一.序列化 类似于Java的序列化:将对象——>文件 如果一个类实现了Serializable接口,这个类的对象就可以输出为文件 同理,如果一个类实现了的Hadoop的序列化机制(接口:Writ ...
- 大数据笔记(七)——Mapreduce程序的开发
一.分析Mapreduce程序开发的流程 1.图示过程 输入:HDFS文件 /input/data.txt Mapper阶段: K1:数据偏移量(以单词记)V1:行数据 K2:单词 V2:记一次数 ...
- 大数据学习(4)MapReduce编程Helloworld:WordCount
Maven依赖: <dependency> <groupId>jdk.tools</groupId> <artifactId>jdk.tools< ...
- 《Data-Intensive Text Processing with mapReduce》读书笔记之二:mapreduce编程、框架及运行
搜狐视频的屌丝男士第二季大结局了,惊现波多野老师,怀揣着无比鸡冻的心情啊,可惜随着剧情的推进发展,并没有出现期待中的屌丝奇遇,大鹏还是没敢冲破尺度的界线.想百度些种子吧,又不想让电脑留下污点证据,要知 ...
- 跟上节奏 大数据时代十大必备IT技能
跟上节奏 大数据时代十大必备IT技能 新的想法诞生新的技术,从而造出许多新词,云计算.大数据.BYOD.社交媒体……在互联网时代,各种新词层出不穷,让人应接不暇.这些新的技术,这些新兴应用和对应的IT ...
- 大数据技术之Hadoop(MapReduce)
第1章 MapReduce概述 1.1 MapReduce定义 1.2 MapReduce优缺点 1.2.1 优点 1.2.2 缺点 1.3 MapReduce核心思想 MapReduce核心编程思想 ...
- 跟上节奏 大数据时代十大必备IT技能(转)
新的想法诞生新的技术,从而造出许多新词,云计算.大数据.BYOD.社交媒体……在互联网时代,各种新词层出不穷,让人应接不暇.这些新的技术,这些新兴应用和对应的IT发展趋势,使得IT人必须了解甚至掌握最 ...
- 大数据笔记01:大数据之Hadoop简介
1. 背景 随着大数据时代来临,人们发现数据越来越多.但是如何对大数据进行存储与分析呢? 单机PC存储和分析数据存在很多瓶颈,包括存储容量.读写速率.计算效率等等,这些单机PC无法满足要求. 2. ...
随机推荐
- [Web 前端] 022 js 的基本数据类型及使用
1. Javascript 基本数据类型 1.1 分类 类型 释义 boolean 布尔类型,分 true 与 false number 整型,浮点型 string 字符类型 object 对象类型 ...
- go io库
1 io.Reader和io.Writer的获取 tcp协议下的io.Reader是从conn中获取到的,因为要先建立conn,conn建立成功之后,然后读写数据. 2 真正的读写 2.1 io.Co ...
- 字符串中的replace方法
String.prototype.replace() 该方法作为字符串中非常常用的方法, 今天我们具体介绍一下它的用法 语法格式 someString.replace(regxp | substr, ...
- 秒懂Vuejs、Angular、React原理和前端发展历史
「前端程序发展的历史」 「 不学自知,不问自晓,古今行事,未之有也 」 我们都知道现在流行的框架:Vue.Js.AngularJs.ReactJs,已经逐渐应用到各个项目和实际应用中,它们都是MVVM ...
- Spring boot项目集成Neo4j
第一步,创建Springboot工程 使用Eclipse 创建Maven项目,并修改pom.xml文件为: <?xml version="1.0" encoding=&quo ...
- 理解 OutOfMemoryError 异常
OutOfMemoryError 异常应该可以算得上是一个非常棘手的问题.JAVA 的程序员不用像苦逼的 C 语言程序员手动地管理内存,JVM 帮助他们分配内存,释放内存.但是当遇到内存相关的问题,就 ...
- Consider defining a bean of type 'org.springframework.web.client.RestTemplate' in your configuration
https://www.cnblogs.com/EasonJim/p/7546136.html 错误如下: ERROR 31473 --- [ main] o.s.b.d.LoggingFailure ...
- Thinkphp5 手册
thinkphp5 手册 https://www.kancloud.cn/manual/thinkphp5/118003
- 安装SQL2005数据库服务时报错处理方法
运行一个脚本,以管理员身份运行: net stop winmgmt c: cd %systemroot%/system32/wbem rd /S /Q repository regsvr32 /s % ...
- nodejs 遍历目录
1 var fs = require("fs"), path = require("path"); function walk(dir, callback) { ...