2016-08-12 1 views
0

ディレクトリ内のファイルを読み取ろうとしています。そのパスはMapReduceプログラムの引数として指定されています。目的は、各ファイル(特定の単語の出現数)で何らかの計算を実行することです。また、ファイルの名前はパターン(例えば.javaファイル)と一致しなければなりません。プログラムの出力は、計算の値とともにファイルの名前です。MapReduceで特定のパターンに一致するディレクトリ内のファイルを読み取り、個々のファイルの名前を出力します。

これまで、私は非常に基本的なMapプログラムを実装することができました。これは、特定のパターンなしでディレクトリの内容を読み取り、ファイル名と定数を出力します。マッパーコードは次のようになります

public class CCMapper extends Mapper<LongWritable, Text, Text, IntWritable>{ 
    private static IntWritable complexityCount = new IntWritable(1); 
    private Text result = new Text(); 

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

     String fileName = ((FileSplit) context.getInputSplit()).getPath().getName(); 
     result.set(filePathString); 
     context.write(result, complexityCount); 

    } 
} 

入力ディレクトリには、file1、file2、file3の3つのファイルがあります。しかし、このプログラムの出力は、私は、各ファイルの出力1の出現にプログラムを入手するにはどうすればよいこの

file1.txt 1 
file1.txt 1 
file1.txt 1 
file1.txt 1 
file1.txt 1 
file1.txt 1 
file1.txt 1 
file2.txt 1 
file2.txt 1 
file2.txt 1 
file2.txt 1 
file3.txt 1 

ようになります。また、一度に1つのファイルを読み込み、そのファイルの計算を実行して、ファイル名と結果を出力する方法もありますか? InputSplitの値を各特定のファイルのサイズに合わせて変更するにはどうすればよいですか?

答えて

1

私はあなたのコードが各ファイルの内容を読み込んでいることを理解しています。 File1には7行が必要です。したがって、キー値のペアは各行に1回 "File1.txt 1"です。 同様に、File2.txtには4行、File3.txtには1行が必要です。

各ファイルを1回出力するには、キーに基づいて値を合計するためにreduce関数でコードを記述する必要があります。

public static class Reduce extends Reducer<Text, IntWritable, Text, IntWritable> { 

@Override 
public void reduce(Text key, Iterable<IntWritable> values, Context context) throws IOException, InterruptedException { 
    int sum = 0; 
    for (IntWritable value : values) { 
    sum += value.get(); 
    } 

    context.write(key, new IntWritable(sum)); 
} 

}

関連する問題