您的位置:首页 > 编程语言

【3-3】Wordcount代码编写

2016-01-25 23:39 369 查看
面试:mapreduce的执行流程是什么?等等。。

打开eclipse,往那个项目里导入mapreduce相关的jar包,jar包的位置:

等以后去了大公司,大家一起开发工作,jar包不能冲突,我们都使用maven,有个maven库,只要配置好home文件

Q:mapreduce分两个阶段,我要用mapreduce这个编程模型,我怎么让他知道这个是mapreduce程序啊?

要么实现接口,要么继承它的类。

因此,自定义一个类,继承mapper这个类,再自定义一个类,继承reducer这个类

我新建一个类,叫MCMapper,这个类应该继承某个类,或实现某个接口,然后我把我自己定义的mapper和reducer提交上去。

因此,我用它extends Mapper



这里面是泛型。Mapper里面有4个泛型,用来约束输入和输出的类型。

KEYIN:输入K1的类型【数字类型long】

VALUEIN:V1的类型【String】

KEYOUT:输出K2类型【long】

VALUEOUT

泛型弄好了,因为我继承了这个类,我要重写方法,选住Mapper shift+Alt+s,点击“覆盖/实现方法”



mapreduce分为两个阶段,你只需要重写它各自的map方法和reduce方法就可以了。

等一下,由于hadoop没有使用jdk默认的序列化机制(因为效率太低),而是自己有一套序列化机制。hadoop2有两个序列化机制,自己的,和谷歌的一个。

因此Long这个类型的就不行了,应该变成LongWritable,String变成Text【注意,由于text导包的时候容易导错,因为太多了,org.hadoop.io下面的包才是对的】

变成如下这样



接下来就可以实现我的map方法了。在这里面key没用到,只用到value就可以了。

public class WCMapper extends Mapper<LongWritable, Text, Text, LongWritable> {

@Override
protected void map(LongWritable key, Text value,
org.apache.hadoop.mapreduce.Mapper.Context context)
throws IOException, InterruptedException {
//接收数据
String line = value.toString();//value是text类型,我要把它转换成string
//现在转换好的是一行内容,接下来要切分数据
String[] words = line.split(" ");
//循环words
for(String w:words){
//出现一次记一个1,输出用.write
context.write((new Text(w),new LongWritable(1));//不能直接write w,w是string类型的,转换成text,v2是longwritable类型的,new一个
}
}

}


接下来再新建一个reducer类,叫WCReducer

package cn.itcast.hadoop.mr;

import java.io.IOException;

import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Reducer;

public class WCReducer extends Reducer<Text, LongWritable, Text, LongWritable>{

@Override
protected void reduce(Text k2, Iterable<LongWritable> v2s,
Context context)//context是reducer的一个内部类,把前面的删了
throws IOException, InterruptedException {
// TODO 自动生成的方法存根
//接收数据
Text k3 = k2;
//定义一个计数器
long counter = 0;
//循环v2s,用增强for循环
for(LongWritable i: v2s){
counter +=i.get();//i本来是longwritable的,用get包装?不太懂,不过成功了

}
//输出
context.write(key,new LongWritable(counter));

}

}


我们自定义了一个mapper和一个reducer,接下来,我们要把这个mapper和reducer告诉我们的mapreduce,因此,我们要把mapper和reducer组装起来。【有个对象,提交上去,

package cn.itcast.hadoop.mr;

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.mapreduce.Job;
import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat;

public class WordCount {

public static void main(String[] args) {
// TODO 自动生成的方法存根

}
//把mapreduce作业抽象成为了一个job对象,然后通过这个对象将我们自定义的mapper和reducer组装起来
//构建job对象
Job job = new Job.getInstance(new Configuration());

//注意,一定要把main方法所在的类设置进去
job.setJarByClass(WordCount.class);

//组装,设置mapper相关属性
job.setMapperClass(WCMapper.class)
job。setMapOutputKeyClass(Text.class)//设置mapper输出的key类型,也就是K2,String不能在hadoop进行网络传输
job。setMapOutputValueClass(LongWritable.class)
//给设置个hdfs路径,让我的mapreduce知道我在哪里读取
FileInputFormat.setInputPaths(job, new Path("/words.txt"));//这个路径是hadoop文件系统上的

//设置reducer相关属性
job.setReducerClass(WCReducer.class);
job.setOutputKeyClass(Text.class);//没指定是哪个输出
job.setOutputValueClass(LongWritable.class);
FileOutputFormat.setOutputPath(job, new Path("/wcout619"));

//job已经组装好了,也设置了属性,接下来把作业提交
job.waitForCompletion(true);

}


这三个都弄好了之后,打成jar包。右键——export——jar file【用hadoop -jar执行,如果是runnable jar 用Java.jar】



点next,让你选所有含有main方法的列出来,让你选,你选Wordcount。这样就把jar包打好了。因为Windows下没有hadoop环境,因此要把这个jar包提交到Linux上
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: