hadoop --- MapReduce

MapReduce定义:

MapReduce可以分解为Map (映射) + Reduce (规约) , 具体过程: 

  1.  Map : 输入数据集被切分成多个小块,并分配给不同的计算节点进行处理
  2. Shuffle and Sort:洗牌和排序,在 Map 阶段结束后,将每个 Mapper 生成的键值对按照键进行排序,并将相同键的值归并在一起,并将相同的键发送给后续的reduce
  3. Reduce: 规约计算,每个计算节点独立处理它们的键值对,并生成最终的输出结果。

 MapReduce是一个分布式运算程序的编程框架,用于用户开发“基于Hadoop的数据分析应用”的核心框架。f核心功能是将用户编写的业务逻辑代码和自带默认组件整合成一个完整的分布式运算程序,并发运行在一个Hadoop集群上。

优点:

  1. 易于编程:用户只关心,业务逻辑。实现框架的接口。
  2. 良好扩展性:可以动态增加服务器,解决计算资源不够问题
  3. 高容错性:任何一台机器挂掉,可以将任务转移到其他节点。
  4. 并行处理:能够有效地利用集群中多个计算节点进行并行计算,提高处理速度。
  5. 适合海量数据计算(TB、PB)几千台服务器共同计算

缺点:

  1. 不擅长实时计算。Mysql
  2. 不擅长流式计算。Sparkstreaming flink
  3. 不擅长DAG有向无环图计算。Spark 

MapReduce架构: 

        MapReduce中,执行MapReduce任务的机器角色有两种: JobTracker 和 TaskTracker, 其中JobTracker 用于任务调度, TaskTracker用于执行任务。 一个Hadoop集群中, 只有一台JobTracker。

 当Client向JobTracker提交作业时, JobTracker会讲作业拆分到多个TaskTracker去执行, TaskTracker会定时发送心跳信息,如果一段时间JobTracker未收到TaskTracker的心跳信息,则认定该TaskTracker出现故障, 会讲该TaskTracker的任务分配给其他TackTracker。

MapReduce执行过程: 

  1.  客户端启动一个job
  2. 客户端向JobTracker请求一个JobID
  3. JobClient讲运行作业所需要的资源复制到HDFS上, 包括jar文件、配置文件、客户端计算所得的输入划分信息,并存档在以JobID 为名的文件夹中。
  4. JobClient 提交任务给JobTracker.
  5. JobTracker 调度作业,并根据输入划分信息为每一个划分创建一个map任务,并将map任务分配给taskTracker执行。【图中的5/6步骤】
  6. TaskTracker每隔一段时间给JobTracker发送一个Heartbeat告诉JobTracker它仍然在运行,同时心跳还携带很多比如map任务完成的进度等信息。当JobTracker收到作业的最后一个任务完成信息时,便把作业设置成“成功”,JobClient再传达信息给用户。

MapReduce wordCount的案例: 

hadoop数据类型
Java类型Hadoop Writable类型
BooleanBooleanWritable
ByteByteWritable
IntIntWritable
FloatFloatWritable
LongLongWritable
DoubleDoubleWritable
StringText
MapMapWritable
ArrayArrayWritable
NullNullWritabl

统计文档中单词出现的频次

1、引入pom依赖: 

    <dependency>
        <groupId>org.apache.hadoop</groupId>
        <artifactId>hadoop-client</artifactId>
        <version>3.1.3</version>
    </dependency> 

2、序列化类 Writable

【当前案例中并未使用到自定义的序列化接口】

Hadoop有自己的序列化机制--Writable, 相比于Java的序列化,hadoop的序列化更紧凑、快速、支持多语言。

Hadoop的序列化步骤: 

  1. 实现Writable接口
  2. 反序列化时需要调用无参构造,所以序列化对象必须要有无参构造
  3. 重写序列化方法write() 
  4. 重写反序列化方法readFidlds()
  5. 反序列化的顺序和序列化的顺序必须完全一致 
  6. 重写toString() ,将结果显示在文件中 
  7. 实现Comparable接口,将自定义的序列化对象放在key中传输
//1 实现Writable接口
@Data
public class FlowBeanWritable implements Writable, Comparable<FlowBeanWritable> {
    private long upFlow; 
    private long downFlow; 
    private long sumFlow; 
    //2 提供无参构造
    public FlowBeanWritable() { }
     
    //4 实现序列化和反序列化方法,注意顺序一定要保持一致
    @Override
    public void write(DataOutput dataOutput) throws IOException {
        dataOutput.writeLong(upFlow);
        dataOutput.writeLong(downFlow);
        dataOutput.writeLong(sumFlow);
    }

    @Override
    public void readFields(DataInput dataInput) throws IOException {
        this.upFlow = dataInput.readLong();
        this.downFlow = dataInput.readLong();
        this.sumFlow = dataInput.readLong();
    }

    //5 重写ToString
    @Override
    public String toString() {
        return upFlow + "\t" + downFlow + "\t" + sumFlow;
    }

    // 6 如果作为Key传输,则还需要实现compareTo方法
    @Override
	public int compareTo(FlowBeanWritable o) {
		// 倒序排列,从大到小
		return this.sumFlow > o.getSumFlow() ? -1 : 1;
	}
}

3、编写Mapper 类,实现Mapper接口

public class WordCountMapper extends Mapper<LongWritable, Text, Text, IntWritable> {
    private Text outK = new Text();
    private IntWritable outV = new IntWritable(1);

    @Override
    protected void map(LongWritable key, Text value, Mapper<LongWritable, Text, Text, IntWritable>.Context context) throws IOException, InterruptedException {
        // 1 获取一行并将其转成String类型来处理
        String line = value.toString();
        // 2 将String类型按照空格切割后存进String数组
        String[] words = line.split(" ");
        // 3 依次取出单词,将每个单词和次数包装成键值对,写入context上下文中供后续调用
        for (String word : words) {
            // 先将String类型,转为text,再包装成健值对
            outK.set(word);
            context.write(outK, outV);
        }
    }
}

Mapper<LongWritable, Text, Text, IntWritable> 泛型里面有四个类, 这里其实是两对键值对:

  1. LongWritable 、Text :表示输入数据,LongWritable表示数据的索引,类似于第几行数据; Text表示读取的文件内容。一般使用系统默认的键值对。
  2. Text、IntWritable: 表示输出数据, Text表示输入的单词, IntWritable表示该单词出现的次数。这个键值对需要根据业务需求来确定。

4、编写Reducer类,继承Reduce抽象类

public class WordCountReducer extends Reducer<Text, IntWritable, Text, IntWritable> {
    IntWritable outV = new IntWritable();

    @Override
    protected void reduce(Text key, Iterable<IntWritable> values, Reducer<Text, IntWritable, Text, IntWritable>.Context context) throws IOException, InterruptedException {
        int sum = 0;
        for (IntWritable value : values) {
            sum += value.get();
        }
        outV.set(sum);
        //写出
        context.write(key,outV);
    }
}

Reducer<Text, IntWritable, Text, IntWritable>  泛型里面有四个类, 这里也是两对键值对:

  • Text, IntWritable:第一个键值对,要跟Mapper的输出泛型保持一致
  • Text, IntWritable:第二个键值对,表示输出的结果数据,因为这里要输出的是单词出现的次数,所以还是 Text、IntWritable 类型 

Reduce是每组会执行一次,就是相同的key是会分到同一组的,所以此处只需计算每个key的count叠加即可

5、编写Driver驱动类 


import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.IntWritable;
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 java.io.IOException;

public class WordCountDriver {

    public static void main(String[] args) throws IOException, ClassNotFoundException, InterruptedException {
        // 获取配置信息以及job对象
        Configuration conf = new Configuration();
        Job job = Job.getInstance(conf);

        // 关联当前Driver程序的jar
        job.setJarByClass(WordCountDriver.class);

        // 指定Mapper和Reducer
        job.setMapperClass(WordCountMapper.class);
        job.setReducerClass(WordCountReducer.class);

        // 设置输入、输出的k、v类型
        job.setMapOutputKeyClass(Text.class);
        job.setMapOutputValueClass(IntWritable.class);
        job.setOutputKeyClass(Text.class);
        job.setOutputValueClass(IntWritable.class);

        // 设置输入输出路径
        FileInputFormat.setInputPaths(job, new Path(args[0]));
        FileOutputFormat.setOutputPath(job, new Path(args[1]));

        // 将job提交给yarn运行
        Boolean result = job.waitForCompletion(Boolean.TRUE);
    }

}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/38403.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Versal ACAP在线升级之Boot Image格式

1、简介 Xilinx FPGA、SOC器件和自适应计算加速平台&#xff08;ACAPs&#xff09;通常由多个硬件和软件二进制文件组成&#xff0c;用于启动这些设备后按照预期设计进行工作。这些二进制文件可以包括FPGA比特流、固件镜像、bootloader引导程序、操作系统和用户选择的应…

使用nginx部署前后端分离项目,处理跨域问题(共享cookie)

1.唠嗑 踩坑了&#xff0c;花费一天时间&#xff0c;开始对nginx配置不懂&#xff0c;老是弄错了配置文件&#xff0c;之前装的nginx ,cofnig有两个&#xff0c;nginx.config和nginx.config.def &#xff0c;开始配置我在nginx.config中配置的&#xff0c;后面一直在改def&…

谈谈VPN是什么、类型、使用场景、工作原理

作者&#xff1a;Insist-- 个人主页&#xff1a;insist--个人主页 作者会持续更新网络知识和python基础知识&#xff0c;期待你的关注 前言 本文将讲解VPN是什么、以及它的类型、使用场景、工作原理。 目录 一、VPN是什么&#xff1f; 二、VPN的类型 1、站点对站点VPN 2、…

「车型分析」控制系统典型应用车型 —— 停车机器人

如今&#xff0c;城市可用土地的日益稀缺&#xff08;城市化&#xff09;和汽车使用数量的增加&#xff08;机动化&#xff09;,为了可持续性发展和其他生活质量问题相结合&#xff0c;由此孕育出来了一种自动停车系统。停车机器人凭借其灵活、高效、标准化的停车模式&#xff…

day27 贪心算法

1.什么是贪心&#xff1f; 比如10张钞票&#xff0c;有1&#xff0c;5&#xff0c;20&#xff0c;100等面额&#xff0c;取五张&#xff0c;如何取得到数额最多的钱&#xff1f;每次取面额最大的那张钞票&#xff1b;就是每个阶段的局部最优&#xff1b;全局最优就是最后拿到的…

【高并发网络通信架构】3.引入IO多路复用(select,poll,epoll)实现高并发tcp服务端

目录 一&#xff0c;往期文章 二&#xff0c;基本概念 IO多路复用 select 模型 poll 模型 epoll 模型 select&#xff0c;poll&#xff0c;epoll 三者对比 三&#xff0c;函数清单 1.select 方法 2.fd_set 结构体 3.poll 方法 4.struct pollfd 结构体 5.epoll_cre…

plt绘图绘制主次刻度线

这里主要是介绍的坐标轴上的主次刻度的划分&#xff0c;这里需要单独引入ticker中的两个模块进行设置 MultipleLocator, FormatStrFormatter set_major_locator() 设置主刻度set_minor_locator() 设置次刻度set_major_formatter() 设置主刻度格式plt.NullLocator() 删除刻度显…

WPS/Office Excel 方向键无法切换表格

问题&#xff1a;WPS/Office Excel 方向键无法切换表格。 分析&#xff1a;键盘开启了Scroll Lock&#xff0c;导致Excel开启了滚动锁定。滚动锁定如图: 解决&#xff1a;再次按下Scroll Lock键解锁即可。&#xff08;Scroll Lock键在键盘右侧上方。&#xff09;

Java设计模式之行为型-解释器模式(UML类图+案例分析)

目录 一、基础概念 二、UML类图 三、角色设计 四、案例分析 五、总结 一、基础概念 解释器模式是指给定一个语言&#xff08;表达式&#xff09;&#xff0c;来表示它的文法&#xff0c;并定义一个解释器&#xff0c;使用该解释器来解释语言中的句子&#xff08;表达式&a…

小奇猫物语之产品经理篇(2)

小奇猫物语之产品经理篇&#xff08;2&#xff09; 喵喵提示&#xff1a;小奇的产品经理篇&#xff08;2&#xff09;来咯&#xff0c;预告一下&#xff0c;前面几篇主要是讲产品经理的思维模式以及怎样去从一个学生思维转变成一个能带领一个项目的产品经理思维&#xff0c;所…

CSDN发表文章的常用语法说明

CSDN常用语法说明 一、标题二、文本样式三、列表四、图片五、链接六、目录一级目录二级目录三级目录 七、表格八、注释九、自定义列表十、LaTeX 数学公式十一、插入甘特图十二、插入UML图十三、插入Mermaid流程图十五、插入Flowchart流程图十六、 插入类图十七、快捷键十八、脚…

macOS Sonoma 14beta 3 (23A5286i)第二个更新「附黑/白苹果镜像下载」

系统镜像下载&#xff1a; 系统介绍 黑果魏叔 7 月12 日消息&#xff0c;苹果今天发布 macOS Sonoma 14.0 Beta 3&#xff08;内部版本号&#xff1a;23A5286i&#xff09;第二个更新。 目前尚不清楚苹果为什么要发布 macOS Sonoma Beta 3 的第二个版本&#xff0c;但它可能…

WooCommerce适合企业电子商务吗?

目录 成功开展电子商务业务变得比以往任何时候都容易。市场上有几个现成的平台&#xff0c;完全有可能将一个初步的想法快速转变为在线贸易业务&#xff0c;并源源不断地收到订单。 什么是 WooCommerce&#xff1f; 为什么您应该考虑使用 WooCommerce 很灵活 重量轻且功…

家政服务小程序软件解决方案

家政服务小程序软件是近年来随着人们对家政服务需求的增长而逐渐兴起的一种数字化服务解决方案。通过小程序软件&#xff0c;用户可以轻松预约家政服务&#xff0c;包括保姆、月嫂、钟点工等&#xff0c;而且价格透明、服务规范&#xff0c;大大提高了用户对家政服务的满意度。…

C++ cin

cin 内容来自《C Primer》 cin使用>>运算符从输入流中抽取字符 int carrots;cin >> carrots;如下的例子&#xff0c;用户输入的字符串有空格 #include <iostream>int main() {using namespace std;const int ArSize 20;char name[ArSize]; //用户名char …

nodejs 下载地址 阿里云开源镜像站

nodejs 下载地址 阿里云开源镜像站 https://mirrors.aliyun.com/nodejs-release/ 我们下期见&#xff0c;拜拜&#xff01;

Vue3的watchEffect的妙用,与watch的区别

前言 在Vue3中&#xff0c;引入了Composition API&#xff0c;其中的watchEffect()函数是一个非常强大和灵活的工具&#xff0c;用于处理响应式数据的变化&#xff0c;使得项目更加弹性和灵活。它与watch有所不同&#xff0c;本文将介绍watchEffect()的定义、特点、与watch的区…

24 MFC文档串行化和单文档应用程序

文章目录 文档串行化全部代码 单文档应用程序搭建原理搭建框架Win32 过度到MFC 三部曲设置ID资源全部代码 单文档应用程序设置标题绘图 简单的管理系统部分代码 文档串行化 ui 设计 保存 void CfileDemoDlg::OnBnClickedBtnSave() {UpdateData();//CFile file(L"Demo.dat…

linux驱动开发:驱动开发框架,linux内核字符设备驱动开发过程

一、驱动框架 1.Linux内核模块和字符驱动的关系 模块是Linux进行组建管理的一种方式, 结构体:对设备的管理内核需要抽象出来一个结构体来描述设备所有的共性信息写驱动需要申请一个结构体并赋值(初始化),然后注册给内核让内核统一管理 驱动:由内核统一管理,所以驱动…

Flask_自定义flask的cmd命令

创建自定义命令 from flask import Flaskapp Flask(__name__)app.cli.command() def hello():"""命令说明写这里"""print("hello python")if __name__ __main__:app.run() 执行flask --help 可以在命令查看定义的命令 注意事项&a…