Hadoop学习(三) Map/Reduce编程

简介: 用Java编程演示如何来实现Map/Reduce编程。其核心思想是通过Map函数,将一个大的任务拆分成若干个小的子任务,交给计算机去并行处理,全部处理结束后由Reducer函数来合并子任务的计算结果,产生最终结果。这样的计算方式将大大缩短计算时间。

WordCount是一个简单的应用,它读入文本文件,然后统计出字符出现的频率。输入是文本文件,输出也是文本文件,它的每一行包含了一个字符和它出现的频率,用一个制表符隔开。这是一个入门的Map/Reduce编程例子,可以说是Map/Reduce版的Hello,World.

先随便找一个英文的文本文件,重新命名为a01.dat,通过Upload files to DFS,将a01.dat文件上传到DFS中。

在新建项目向导中,新建一个Map/Reduce项目。一个Map/Reduce项目,包含三个主要文件,一个是Map文件,一个是Reduce文件,还有一个是主文件。源代码如下:

Map.java

    import java.io.IOException;
    import java.util.*;
    import org.apache.hadoop.io.*;
    import org.apache.hadoop.mapreduce.Mapper;

    public class Map extends Mapper<LongWritable, Text, Text, IntWritable> {
        private final static IntWritable one = new IntWritable(1);
        private Text word = new Text();
        public void map(LongWritable key, Text value, Context context) throws IOException, InterruptedException {
            String line = value.toString();
            StringTokenizer tokenizer = new StringTokenizer(line);
            while (tokenizer.hasMoreTokens()) {
                word.set(tokenizer.nextToken());
                context.write(word, one);
            }
        }
     } 

Reduce.java

    import java.io.IOException;
    import org.apache.hadoop.io.*;
    import org.apache.hadoop.mapreduce.*;

    public class Reduce extends Reducer<Text, IntWritable, Text, IntWritable> {
        public void reduce(Text key, Iterable<IntWritable> values, Context context) 
          throws IOException, InterruptedException {
            int sum = 0;
            for (IntWritable val : values) {
                sum += val.get();
            }
            context.write(key, new IntWritable(sum));
        }
     }

WordCount.java

    import org.apache.hadoop.fs.Path;
    import org.apache.hadoop.conf.*;
    import org.apache.hadoop.io.*;
    import org.apache.hadoop.mapreduce.*;
    import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
    import org.apache.hadoop.mapreduce.lib.input.TextInputFormat;
    import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat;
    import org.apache.hadoop.mapreduce.lib.output.TextOutputFormat;
            
    public class WordCount {
            
      public static void main(String[] args) throws Exception {
        Configuration conf = new Configuration();
        Job job = new Job(conf, "wordcount");
        job.setOutputKeyClass(Text.class);
        job.setOutputValueClass(IntWritable.class);
        job.setMapperClass(Map.class);
        job.setReducerClass(Reduce.class);
        job.setInputFormatClass(TextInputFormat.class);
        job.setOutputFormatClass(TextOutputFormat.class);
        FileInputFormat.addInputPath(job, new Path("hdfs://localhost:9000/a01.dat"));
        FileOutputFormat.setOutputPath(job, new Path("hdfs://localhost:9000/output"));
        job.waitForCompletion(true);
        }
    }

选择Run As - Run on Hadoop

运行结果存放在output路径下,可以通过http://localhost:50070/查看。

该程序将文本文件的输入,通过Map函数,转换成一组 key,value 有序对。然后根据key,合并成 key,value1,value2....,然后再通过Reducer函数,做累加操作,计算出每个单词的出现次数,生成新的 key,sum 有序对后输出。

手头上有个邮件列表,包含了几万个邮件地址,于是修改了一下map函数,统计各个邮箱的使用情况。修改后的map为:

    public void map(LongWritable key, Text value, Context context) 
        throws IOException, InterruptedException {
        String[] sarray=value.toString().split("@");
        word.set(sarray[1]);
        context.write(word, one);
    }

运行后得到以下结果:

      126.com 17230
      139.com 573
      163.com 35928
      21cn.com  1372
      citiz.net 223
      eyou.com  385
      foxmail.com 143
      gmail.com 2228
      hotmail.com 11021
      live.cn 437
      msn.com 562
      qq.com  22185
      sina.com  9671
      sina.com.cn 540
      sogou.com 222
      sohu.com  4106
      tom.com 2676
      vip.163.com 129
      vip.qq.com  589
      vip.sina.com  355
      vip.sohu.com  285
      yahoo.cn  14607
      yahoo.com 315
      yahoo.com.cn  10770
      yahoo.com.hk  252
      yeah.net  828
目录
相关文章
|
3月前
|
Python
高阶函数如`map`, `filter`, `reduce`和`functools.partial`在Python中用于函数操作
【6月更文挑战第20天】高阶函数如`map`, `filter`, `reduce`和`functools.partial`在Python中用于函数操作。装饰器如`@timer`接收或返回函数,用于扩展功能,如记录执行时间。`timer`装饰器通过包裹函数并计算执行间隙展示时间消耗,如`my_function(2)`执行耗时2秒。
26 3
|
3天前
|
分布式计算 Hadoop Java
面向开发者的Hadoop编程指南
【8月更文第28天】Hadoop是一个开源软件框架,用于分布式存储和处理大规模数据集。它由Hadoop分布式文件系统(HDFS)和MapReduce编程模型组成。本指南旨在帮助初学者和中级开发者快速掌握Hadoop的基本概念和编程技巧,并通过一些简单的示例来加深理解。
13 0
|
2月前
|
人工智能 算法 大数据
算法金 | 推导式、生成器、向量化、map、filter、reduce、itertools,再见 for 循环
这篇内容介绍了编程中避免使用 for 循环的一些方法,特别是针对 Python 语言。它强调了 for 循环在处理大数据或复杂逻辑时可能导致的性能、可读性和复杂度问题。
37 6
算法金 | 推导式、生成器、向量化、map、filter、reduce、itertools,再见 for 循环
|
24天前
|
分布式计算 Python
【python笔记】高阶函数map、filter、reduce
【python笔记】高阶函数map、filter、reduce
|
2月前
|
JavaScript API
js【最佳实践】遍历数组的八种方法(含数组遍历 API 的对比)for,forEach,for of,map,filter,reduce,every,some
js【最佳实践】遍历数组的八种方法(含数组遍历 API 的对比)for,forEach,for of,map,filter,reduce,every,some
45 1
|
2月前
|
存储 C++ 索引
|
3月前
|
Python
在Python中,`map()`, `filter()` 和 `reduce()` 是函数式编程中的三个核心高阶函数。
【6月更文挑战第24天】Python的`map()`应用函数到序列元素,返回新序列;`filter()`筛选满足条件的元素,生成新序列;`reduce()`累计操作序列元素,返回单一结果。
29 3
|
3月前
|
存储 自然语言处理 C++
【C++航海王:追寻罗杰的编程之路】set|map|multiset|multimap简单介绍
【C++航海王:追寻罗杰的编程之路】set|map|multiset|multimap简单介绍
32 0
【C++航海王:追寻罗杰的编程之路】set|map|multiset|multimap简单介绍
|
3月前
|
分布式计算 Hadoop Java
Hadoop MapReduce编程
该教程指导编写Hadoop MapReduce程序处理天气数据。任务包括计算每个城市ID的最高、最低气温、气温出现次数和平均气温。在读取数据时需忽略表头,且数据应为整数。教程中提供了环境变量设置、Java编译、jar包创建及MapReduce执行的步骤说明,但假设读者已具备基础操作技能。此外,还提到一个扩展练习,通过分区功能将具有相同尾数的数字分组到不同文件。
41 1
|
4月前
|
存储 Java
【JAVA学习之路 | 进阶篇】Map接口及其实现类及常用方法
【JAVA学习之路 | 进阶篇】Map接口及其实现类及常用方法

相关实验场景

更多
下一篇
云函数