Hadoop学习笔记之如何运行一个MapReduce程序

Hadoop学习笔记之如何运行一个MapReduce程序

       MapReduce可以分为两个阶段来处理,一个阶段为map,另一个阶段为reduce.每个阶段都有键值对的输入和输出参数,输入输出键值对的类型由程序决定,程序同样指定了两个函数,map函数和reduce函数。
在这里,我们使用NCDC数据作为MapReduce例子的测试数据。
下面具体介绍下最简单的MapReduce.

快速索引:

1.编写Mapper程序

2.编写Reducer程序

3.编写Job Object

4.运行Job

1.编写Mapper程序

       

  1. package com.rickywag.hadoop;  
  2.   
  3. import org.apache.hadoop.io.IntWritable;  
  4. import org.apache.hadoop.io.LongWritable;  
  5. import org.apache.hadoop.io.Text;  
  6. import org.apache.hadoop.mapreduce.Mapper;  
  7. import java.io.IOException;  
  8.   
  9.   
  10. /** 
  11.  * Mapper程序主要用于处理数据,过滤不需要的数据,把需要的程序输出到reduce程序。 
  12.  *  @author Ricky 
  13.  *  @since 2014/08/25 
  14.  */  
  15. public class MaxTemperatureMapper  
  16.         extends Mapper<LongWritable, Text, Text, IntWritable> {  
  17.     private static final int MISSING = 9999;  
  18.   
  19.     /** 
  20.      * map函数主要用于解析NCDC文件中每一行的年份和气温 
  21.      * @param key NCDC文件中信息行数的偏移量 
  22.      * @param value NCDC文件对应行数偏移量的信息 
  23.      * @param context 输出变量 
  24.      * @throws IOException IO异常 
  25.      * @throws InterruptedException 线程中断异常 
  26.      */  
  27.     @Override  
  28.     public void map(LongWritable key, Text value, Context context)  
  29.             throws IOException, InterruptedException {  
  30.         String line = value.toString(); //获取每一行NCDC信息  
  31.         String year = line.substring(1519);//获取每一行的年份  
  32.         //获取每一行的温度  
  33.         int airTemperature;  
  34.         if (line.charAt(87) == '+') { //解析int字符串不需要‘+’  
  35.             airTemperature = Integer.parseInt(line.substring(8892));  
  36.         } else {  
  37.             airTemperature = Integer.parseInt(line.substring(8792));  
  38.         }  
  39.         String quality = line.substring(9293);  
  40.         if (airTemperature != MISSING && quality.matches("[01459]")) {  
  41.             //输出年份,温度到reduce阶段,在输出到reduce之前,mapper会对数据进行排序和分组。  
  42.             context.write(new Text(year), new IntWritable(airTemperature));  
  43.         }  
  44.     }  
  45. }  

2.编写Reducer程序

  1. package com.rickywag.hadoop;  
  2.   
  3. import org.apache.hadoop.io.IntWritable;  
  4. import org.apache.hadoop.io.Text;  
  5. import org.apache.hadoop.mapreduce.Reducer;  
  6.   
  7. import java.io.IOException;  
  8.   
  9. /** 
  10.  * 找出一年中最高的温度 
  11.  *  @author Ricky 
  12.  *  @since 2014/08/25 
  13.  */  
  14. public class MaxTemperatureReducer  
  15.         extends Reducer<Text, IntWritable, Text, IntWritable> {  
  16.   
  17.     /** 
  18.      * 通过map处理过的数据,找出一年中的最高温度 
  19.      * @param key 年份 
  20.      * @param values 该年份的所有温度 
  21.      * @param context 把结果输出到下一个阶段 
  22.      * @throws IOException IO异常 
  23.      * @throws InterruptedException 线程中断异常 
  24.      */  
  25.     @Override  
  26.     public void reduce(Text key, Iterable<IntWritable> values,  
  27.                        Context context)  
  28.             throws IOException, InterruptedException {  
  29.         int maxValue = Integer.MIN_VALUE;//int 类型数据的最小值  
  30.         //找出一年中的最高气温  
  31.         for (IntWritable value : values) {  
  32.             maxValue = Math.max(maxValue, value.get());  
  33.         }  
  34.         //把最高温度的年份作为key,最高的温度作为值,输出到文件中。  
  35.         context.write(key, new IntWritable(maxValue));  
  36.     }  
  37. }  

这是整个MapReduce的流程
mapreduce

3.编写Job Object

  1. package com.rickywag.hadoop;  
  2.   
  3. import org.apache.hadoop.fs.Path;  
  4. import org.apache.hadoop.io.IntWritable;  
  5. import org.apache.hadoop.io.Text;  
  6. import org.apache.hadoop.mapreduce.Job;  
  7. import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;  
  8. import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat;  
  9.   
  10. /** 
  11.  *  控制求最大温度作业的执行 
  12.  *  @author Ricky 
  13.  *  @since 2014/08/25 
  14.  */  
  15. public class MaxTemperature {  
  16.     public static void main(String[] args) throws Exception {  
  17.         /** 
  18.          * input path : NCDC数据文件在HDFS中的位置  
  19.          * output path: MapReduce处理完成后结果存放的位置(默认该路径在HDFS中不存在,若已经存在会抛异常) 
  20.          */  
  21.         if (args.length != 2) {  
  22.             System.err.println("Usage: MaxTemperature <input path> <output path>");  
  23.             System.exit(-1);  
  24.         }  
  25.         Job job = new Job();  
  26.         job.setJarByClass(MaxTemperature.class);//job会查询包涵该类的包。  
  27.         job.setJobName("Max temperature");//设置作业名称  
  28.         FileInputFormat.addInputPath(job, new Path(args[0]));//设置NCDC文件在HDFS存在的位置  
  29.         FileOutputFormat.setOutputPath(job, new Path(args[1]));//设置job运行结果存放的位置  
  30.         job.setMapperClass(MaxTemperatureMapper.class);//设置map阶段执行的代码  
  31.         job.setReducerClass(MaxTemperatureReducer.class);//设置reduce阶段执行的代码  
  32.         job.setOutputKeyClass(Text.class);//设置输出key  
  33.         job.setOutputValueClass(IntWritable.class);//设置输出的值  
  34.         System.exit(job.waitForCompletion(true) ? 0 : 1);//若作业正常执行完成,系统正常退出。  
  35.     }  
  36. }  

4.运行Job

       在运行MapReduce程序之前,需要把MapReduce程序打包成一个可以执行的Jar包。
因为我用的是Maven管理,需要用插件才可以打包成可执行的Jar包。

  1. <?xml version="1.0" encoding="UTF-8"?>  
  2. <project xmlns="http://maven.apache.org/POM/4.0.0"  
  3.          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
  4.          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">  
  5.     <modelVersion>4.0.0</modelVersion>  
  6.   
  7.     <groupId>com.rickywag.hadoop</groupId>  
  8.     <artifactId>hadoop-simpleMapperReducer</artifactId>  
  9.     <version>1.0-SNAPSHOT</version>  
  10.   
  11.     <!-- All developers contact information-->  
  12.     <developers>  
  13.         <developer>  
  14.             <id>Ricky</id>  
  15.             <name>Ricky Lau</name>  
  16.             <email>Ricky_LS@163.com</email>  
  17.             <organization>com.rickywag</organization>  
  18.             <roles>  
  19.                 <role>Project Creater</role>  
  20.             </roles>  
  21.             <timezone>+8</timezone>  
  22.         </developer>  
  23.     </developers>  
  24.   
  25.     <!-- Project Licenses-->  
  26.     <licenses>  
  27.         <license>  
  28.             <name>Apache License, Version 2.0</name>  
  29.             <url>http://www.apache.org/licenses/LICENSE-2.0</url>  
  30.         </license>  
  31.     </licenses>  
  32.   
  33.     <!-- Manage all plugin version-->  
  34.     <properties>  
  35.         <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>  
  36.         <java-version>1.7</java-version>  
  37.         <slf4j.version>1.7.5</slf4j.version>  
  38.         <logback.version>1.0.13</logback.version>  
  39.         <org.apache.commons.lang.version>3.1</org.apache.commons.lang.version>  
  40.         <junit.version>4.11</junit.version>  
  41.     </properties>  
  42.   
  43.   
  44.     <!-- Manager all third party dependency - -->  
  45.     <dependencies>  
  46.         <!-- Log dependency -->  
  47.         <dependency>  
  48.             <groupId>org.slf4j</groupId>  
  49.             <artifactId>slf4j-api</artifactId>  
  50.             <version>${slf4j.version}</version>  
  51.         </dependency>  
  52.   
  53.         <dependency>  
  54.             <groupId>org.slf4j</groupId>  
  55.             <artifactId>jcl-over-slf4j</artifactId>  
  56.             <version>${slf4j.version}</version>  
  57.         </dependency>  
  58.   
  59.         <dependency>  
  60.             <groupId>org.slf4j</groupId>  
  61.             <artifactId>jul-to-slf4j</artifactId>  
  62.             <version>${slf4j.version}</version>  
  63.         </dependency>  
  64.   
  65.         <dependency>  
  66.             <groupId>ch.qos.logback</groupId>  
  67.             <artifactId>logback-classic</artifactId>  
  68.             <version>${logback.version}</version>  
  69.         </dependency>  
  70.   
  71.         <dependency>  
  72.             <groupId>ch.qos.logback</groupId>  
  73.             <artifactId>logback-core</artifactId>  
  74.             <version>${logback.version}</version>  
  75.         </dependency>  
  76.   
  77.         <!-- Junit -->  
  78.         <dependency>  
  79.             <groupId>junit</groupId>  
  80.             <artifactId>junit</artifactId>  
  81.             <version>${junit.version}</version>  
  82.         </dependency>  
  83.   
  84.         <!-- org.apache.commons -->  
  85.         <dependency>  
  86.             <groupId>org.apache.commons</groupId>  
  87.             <artifactId>commons-lang3</artifactId>  
  88.             <version>${org.apache.commons.lang.version}</version>  
  89.         </dependency>  
  90.   
  91.         <!-- hadoop 2.5.0   -->  
  92.   
  93.         <dependency>  
  94.             <groupId>org.apache.hadoop</groupId>  
  95.             <artifactId>hadoop-common</artifactId>  
  96.             <version>2.5.0</version>  
  97.         </dependency>  
  98.   
  99.         <dependency>  
  100.             <groupId>org.apache.hadoop</groupId>  
  101.             <artifactId>hadoop-mapreduce-client-core</artifactId>  
  102.             <version>2.5.0</version>  
  103.         </dependency>  
  104.   
  105.     </dependencies>  
  106.   
  107.     <build>  
  108.         <finalName>hadoop-simpleMapperReducer</finalName>  
  109.         <plugins>  
  110.             <!-- compiler plugin-->  
  111.             <plugin>  
  112.                 <groupId>org.apache.maven.plugins</groupId>  
  113.                 <artifactId>maven-compiler-plugin</artifactId>  
  114.                 <version>3.1</version>  
  115.                 <configuration>  
  116.                     <source>${java-version}</source>  
  117.                     <target>${java-version}</target>  
  118.                     <encoding>${project.build.sourceEncoding}</encoding>  
  119.                     <compilerArgument>-Xlint:all</compilerArgument>  
  120.                     <showWarnings>true</showWarnings>  
  121.                     <showDeprecation>true</showDeprecation>  
  122.                 </configuration>  
  123.             </plugin>  
  124.   
  125.             <plugin>  
  126.                 <groupId>org.apache.maven.plugins</groupId>  
  127.                 <artifactId>maven-shade-plugin</artifactId>  
  128.                 <version>2.3</version>  
  129.                 <executions>  
  130.                     <execution>  
  131.                         <phase>package</phase>  
  132.                         <goals>  
  133.                             <goal>shade</goal>  
  134.                         </goals>  
  135.                         <configuration>  
  136.                             <transformers>  
  137.                                 <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">  
  138.                                     <mainClass>com.rickywag.hadoop.MaxTemperature</mainClass>  
  139.                                 </transformer>  
  140.                             </transformers>  
  141.                         </configuration>  
  142.                     </execution>  
  143.                 </executions>  
  144.             </plugin>  
  145.   
  146.         </plugins>  
  147.   
  148.     </build>  
  149. </project>  

由于maven中央库中没有hadoop 2.5.0的相关jar包,当前的2.5.0是我通过私服自己上传的。默认你们没有私服,但如果你们想用我的程序直接打包,需要把两个hadoop 2.5.0的jar包安装到本地仓库中去。这两个jar包分别位于%HADOOP_INSTALL%/share/hadoop/common/hadoop-common-2.5.0.jar 和 %HADOOP_INSTALL%/share/hadoop/mapreduce/hadoop-mapreduce-client-core-2.5.0.jar

用下面两条命令把两个jar包导入maven本地仓库,把JARPOSITION替换为jar包存放的路径

1.mvn install:install-file -Dfile=JARPOSITION/hadoop-common-2.5.0.jar -DgroupId=org.apache.hadoop -DartifactId=hadoop-common -Dversion=2.5.0 -Dpackaging=jar

2.mvn install:install-file -Dfile=JARPOSITION/hadoop-mapreduce-client-core-2.5.0.jar -DgroupId=org.apache.hadoop -DartifactId=hadoop-mapreduce-client-core -Dversion=2.5.0 -Dpackaging=jar
编译打包MapReduce程序
执行 mvn clean package,获取target下的已经打包好的MapReduce程序,hadoop-simpleMapperReducer.jar。 

3.上传测试数据文件与打包的MapReduce程序至linux 根目录下
测试数据在百度云盘上,若无法使用请发邮件通知。 下载NCDC测试数据
,默认该文件已经下载到linux的根目录下,文件名为1901.

把已经打包好的程序也上传到linux的根性目录下。

4.上传测试数据文件到hdfs上。
cd %HADOOP_INSTALL%

bin/hdfs dfs -put /1901 /

export HADOOP_CLASSPATH=/hadoop-simpleMapperReducer.jar

hadoop com.rickywag.hadoop.MaxTemperature /1901 output

执行完成后,若没有报错,查询1901年的最高温度输出文件

bin/hdfs dfs -cat /user/root/output/part-r-00000 结果如下:

1901 317

到这里,最简单的MapReduce就运行成功了。在写的过程中,由于自己也是现学现卖,我学习的时候hadoop用的版本比较高会导致,有一些老API和新API同时使用的情况,等我了解在多一点的时候,我会抛弃旧的API完全使用新的API.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值