获取单词在文本文件中出现的次数并将其链接到文本文件

时间:2015-10-01 06:12:06

标签: java hadoop mapreduce

我目前有3个带有数据的文本文件

  

Textfile1
  你好世界
  再见世界

     

Textfile2
  你好世界
  你好第二个

如何获得

的结果
  

Hello {Textfile1 = 1,Textfile2 = 2}
  World {Textfile1 = 2,Textfile2 = 1}

目前我已设法将我的Map中的单词传递到我的Reduce java页面。这就是我现在被困住的地方。

public class Reduce extends Reducer<Text, Text, Text, Text> {
    HashMap<Text, Integer>input = new HashMap<Text, Integer>();

    public void reduce(Text key, Iterable<Text> values , Context context)
    throws IOException, InterruptedException {
        int sum = 0;
        for(Text val: values){
            String word = key.toString();
            Text filename;
            input.put(val,sum );
                if(//not sure what to write here){

               }
            }
       context.write(new Text(key), input);
}

我的映射器代码

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

private Text file = new Text();
private Text word = new Text();
private String pattern= "^[a-z][a-z0-9]*$";//any lower case letter or number

public void map(LongWritable key, Text value,Context context) throws IOException, InterruptedException {

    InputSplit inputSplit = context.getInputSplit();
    String fileName = ((FileSplit)inputSplit).getPath().getName();
    file.set(fileName);
    String line = value.toString();
    StringTokenizer tokenizer = new StringTokenizer(line);
    while (tokenizer.hasMoreTokens()) {
       word.set(tokenizer.nextToken());

        String stringWord = word.toString().toLowerCase();
        if (stringWord.matches(pattern)){
            context.write(new Text(stringWord), new Text(fileName));

        }
    }
}

}

希望我能得到一些帮助

2 个答案:

答案 0 :(得分:1)

在mapper的输出中,我们可以将文本文件名设置为键,将文件中的每一行设置为值。

可以使用Mapper类中的以下代码片段检索文件名。

FileSplit fileSplit = (FileSplit)context.getInputSplit();
String filename = fileSplit.getPath().getName();

然后在减速器中

public class Reduce extends Reducer<Text, Text, Text, Text> {
HashMap<Text, Integer>input = new HashMap<Text, Integer>();

public void reduce(Text key, Iterable<Text> values , Context context)
throws IOException, InterruptedException {
    int sum = 0;
    for(Text val: values){
        String word = val.toString(); -- processing each row
        String[] wordarray = word.split(' ');
        for(int i=0 ; i<wordarray.length; i++)
       {
        if(input.get(wordarray[i]) == null){
        input.put(wordarray[i],1);}
        else{
         int value =input.get(wordarray[i]) +1 ; 
         input.put(wordarray[i],value);
         }
       }     

   context.write(new Text(key), new Text(input.toString()));
}

答案 1 :(得分:0)

您可以为地图密钥编写自定义可写类。类似textpair的文件名,文字和值将为1。

地图输出

<K,V> ==> <MytextpairWritable,new IntWritable(1)>

只需总结reducer端的值并发出值即可。这样的事情。

public class Reduce extends Reducer<mytextpairWritable, IntWritable,mytextpairWritable, IntWritable> {


    public void reduce(mytextpairWritable 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));
}

这会给你类似的东西

File1,hello,2
File2,hello,3
File3,hello,1